home *** CD-ROM | disk | FTP | other *** search
/ Aminet 37 / Aminet 37 (2000)(Schatztruhe)[!][Jun 2000].iso / Aminet / dev / debug / SmartCrash.lha / SmartCrash / src / SmartCrash.ASM < prev   
Encoding:
Assembly Source File  |  2000-03-09  |  52.1 KB  |  2,278 lines

  1. ; FILE: Source:SmartCrash.ASM          REV: 184 --- System failure req replacement
  2. ; History
  3. ;  79     Working.
  4. ;  100    Fixed.
  5. ;  150    Fixed alert fallback.
  6. ;  151    Strange crashes with PPC equipped systems.
  7. ;  156    Still trying to fix these crashes.
  8. ;  183    LaunchProc bugged.
  9. ;  184    Froze 1.3.0 aminet.
  10. ;
  11.  
  12. ; Release version 1.3.0
  13.  
  14. ; Total rewrite, removed several hacks & bugs, including:
  15. ; - LaunchProc was bugged (would have crashed)
  16. ; - Removed usage of fixed signal bits, when possible
  17. ; - Removed SegList cutting
  18. ; - Now uses FindTask(0) instead of directly accessing ExecBase ThisTask
  19. ; - Replaced FindName on ExecBase LibList with OpenLibrary calls
  20. ; - Removed several possible race conditions
  21. ; - Now always keeps stack pointer longword aligned
  22. ; - Now does LoadView(0) & 2 x WaitTOF(0) before ColdReboot()
  23. ; - Now if AddTask() fails LaunchTask does FreeEntry() for TCB & stack
  24. ; - Now LaunchTask/LaunchProc make sure stacksize is quodword aligned
  25. ; - No longer passes invalid TextAttr to rtEZRequestA()
  26. ; - Now .ChangeTrapCode checks for SMARTCRASH13_ID from custom TC_TRAPCODE
  27. ; - Added support for PatchControl
  28. ; - Now .remove tries to restore TC_TRAPCODE for every task/process possible
  29. ; - Default task/proc trap handlers are now retrieved properly
  30. ; - 'exit & free' renamed to 'remove'
  31. ; - 'remove' now closes all windows & screens owned by task
  32. ; - Now `skip' handles all 68851/68040/68060/CPU32 f-line emulators and
  33. ;   privilege violations
  34. ; - Now supports 6888x/68040/68060 FPU vectors 48 to 55 and 68060 vectors 60
  35. ;   and 61
  36. ; - Fixed crashes with multiple requesters, these were due bad access of
  37. ;   global CD_Task. See Trap_UserPart
  38. ; - Added support for 68000 bus and address error exception stack frames,
  39. ;   failed miserably before. 68000 uses separate exception handler
  40. ; - No longer uses TC_TRAPCODE to pass arguments but TC_TRAPDATA (wow!)
  41. ; - Now SegTrackerInfo also checks stack at word boundaries
  42. ; - Debug button could have trashed rtEZRequestA() call a1 register on .redo_rtreq,
  43. ;   default void Debug() only does moveq #0,d0;rts so this bug was hiding... :)
  44. ; - New buttons 'rts' (jmp to rts with current stack) and 'jmp...' (jmp to
  45. ;   address entered to a number requester).
  46. ; - Now forces stack address even before CD_StackFrame copy
  47. ; - Can't hang anymore on FindPort/AddPort race condition
  48. ; - More information output on argument error
  49. ;
  50. ; - Currently only hack is to change SS_OWNER to allow different task to
  51. ;   ReleaseSemaphore owned semaphore
  52. ;
  53. ; - Optimized/cleaned up code
  54.  
  55. ; todo (maybe):
  56. ; - FORCE/S replace even unknown (non-dos/exec) trap handlers
  57. ; - SERIAL/S add serial output of any software error before displaying requester
  58. ;   use _LVORawPutChar (-$204)
  59. ;   (these two would be for tnt v37.2 compatibility)
  60. ;
  61. ; - Make use of INSTSIZE ?
  62. ;
  63. ; - New buttons: 'Modify...' '%sDX|%sAX|%sPC|%sSR|run mon|%sCancel' ??
  64. ; - removal of semaphore = use big message to deliver CD ?
  65. ; - parallel and serial support, disassembler?
  66. ; - fpu f-line skip:
  67. ;   o normally fpu instructions are long with fixed pos <ea>
  68. ;   o special cases:
  69. ;     - FBcc
  70. ;     - FDBcc
  71. ;     - FMOVECR
  72. ;     - FNOP
  73. ;     - FTRAPcc .W .L
  74. ;     - cpSAVE    word
  75. ;     - cpRESTORE word
  76.  
  77.     OPT    p=68010,ow-,o+
  78.  
  79.     include    "Devpac:Gen.gs"
  80. ;    include    "dos/dosextens.i"
  81. ;    include    "intuition/intuition.i"
  82.     include    "dos/dostags.i"
  83.     include    "libraries/intuition_lib.i"
  84.     include    "libraries/diskfont_lib.i"
  85.     include    "libraries/reqtools_lib.i"
  86.     include    "libraries/reqtools.i"
  87.  
  88.     include    "requestlong.i"
  89.  
  90. ARG_USEREQTOOLS    EQU    0
  91. ARG_RTFONT    EQU    1
  92. ARG_RTFONTSIZE    EQU    2
  93. ARG_NUMARGS    EQU    3
  94.  
  95. MAXFONTNAMELEN    EQU    32
  96.  
  97.     STRUCTURE MyMes,MN_SIZE
  98.     APTR    MyMes_SigTask
  99.     ULONG    MyMes_InitOkSigMask
  100.     ULONG    MyMes_RemovedSigMask
  101.     LABEL    MyMes_SIZEOF
  102. MyMes_Type    EQU    LN_NAME
  103.  
  104. MMTYPE_REMOVE    EQU    1
  105. MMTYPE_REPORT    EQU    2
  106.  
  107. NUMSCGADGETS    EQU    7            ; reboot doesn't have shortcut!
  108. GADG_SKIP    EQU    1
  109. GADG_REMOVE    EQU    2
  110. GADG_EXIT    EQU    3
  111. GADG_DEBUG    EQU    4
  112. GADG_REBOOT    EQU    5
  113. GADG_Modify    EQU    6
  114. GADG_RTS    EQU    7
  115. GADG_SUSPEND    EQU    0
  116.  
  117. ; 'Modify...'
  118. ; '%sDX|%sAX|%sPC|%sSR|run mon|%sCancel'
  119. ; 'D%s0|D%s1|D%s2|D%s3|D%s4|D%s5|D%s6|D%s7|%sCancel'
  120. ; 'A%s0|A%s1|A%s2|A%s3|A%s4|A%s5|A%s6|A%s7|%sCancel'
  121.  
  122. ACTION_SKIP    EQU    0            skip instruction
  123. ACTION_EXIT    EQU    2            exit program
  124. ACTION_JMP    EQU    4            jump to address in CD_ProgramCounter
  125.  
  126. SMARTCRASH13_ID    EQU    'SC13'
  127. SC13IDPOS    EQU    10            _idpos-TrapEntry
  128.  
  129. WAKE_SIGNAL    EQU    SIGB_SINGLE        4
  130. ;FIXED_SKIPPED_SIGNAL    EQU    23
  131. ;HACKSEMAPHORE    EQU    1
  132. ;FINDTASKBUG    EQU    1
  133. ;INSTSIZE    EQU    1
  134.  
  135.     STRUCTURE CrashDataStruct,0
  136.     STRUCT    CD_MySemaphore,SS_SIZE
  137.     LABEL    CD_CD
  138.     BYTE    CD_TrapNumber
  139.     BYTE    CD_KludgeFill00_1
  140.     UWORD    CD_Action        ; Used with WAKE_SIGNAL, see ACTION_* above
  141.     ULONG    CD_sigf_SKIPPED
  142.     APTR    CD_PrevTRAPDATA
  143.     LONG    CD_ExceptionNumber
  144.     APTR    CD_ExceptionStr1
  145.     APTR    CD_ExceptionStr2
  146.     APTR    CD_ExceptionStr3
  147.     APTR    CD_Task
  148.     APTR    CD_ProgramCounter
  149.     WORD    CD_KludgeFill00_2
  150.     WORD    CD_StatusRegister
  151.     APTR    CD_UserStackPtr
  152.     APTR    CD_SuperStackPtr
  153.     STRUCT    CD_DataRegs,8*4
  154.     APTR    CD_AddrReg_0
  155.     STRUCT    CD_AddrRegs_1_6,6*4
  156.     APTR    CD_StackPtr
  157.     STRUCT    CD_StackFrame,16*4
  158.     APTR    CD_TaskType        ; CLI/Process/Task
  159.     APTR    CD_TaskName
  160.     APTR    CD_SegTrackerInfo
  161.     LABEL    CD_CD_END
  162.     LABEL    CD_SIZE
  163.  
  164.     IFGT    (CD_CD_END-CD_CD)&3
  165.     FAIL    "(CD_CD_END-CD_CD) not longword aligned!"
  166.     ENDC
  167.  
  168. Main    move.l    (4).w,a6
  169.     moveq    #37,d7
  170.     cmp.w    (LIB_VERSION,a6),d7
  171.     bhs    .no37
  172.  
  173.     moveq    #RETURN_ERROR,d7
  174.  
  175.     sub.l    a1,a1
  176.     call    FindTask
  177.     move.l    d0,SigThisTask
  178.  
  179.     ; Allocate signals...
  180.  
  181.     moveq    #-1,d0
  182.     call    AllocSignal
  183.     move.l    d0,sigb_REMOVED
  184.     bmi    .nosig1
  185.     moveq    #1,d1
  186.     lsl.l    d0,d1
  187.     move.l    d1,sigf_REMOVED
  188.  
  189.     moveq    #-1,d0
  190.     call    AllocSignal
  191.     move.l    d0,sigb_INITOK
  192.     bmi    .nosig2
  193.     moveq    #1,d1
  194.     lsl.l    d0,d1
  195.     move.l    d1,sigf_INITOK
  196.  
  197.     ; Open dos
  198.  
  199.     lea    (DosName,pc),a1
  200.     bsr    openlib
  201.     move.l    d0,DosBase
  202.     beq    .nodos
  203.  
  204.     ; Get DefTaskTrap and DefProcTrap
  205.  
  206.     bsr    GetDefTraps
  207.  
  208.     ; Greet
  209.  
  210.     lea    (AboutMessage,pc),a0
  211.     bsr    Printf
  212.  
  213.     ; Test if already installed
  214.  
  215.     lea    (PortName,pc),a1
  216.     call    Forbid
  217.     call    FindPort
  218.     tst.l    d0
  219.     beq.b    .install
  220.  
  221.     ; Send quit request to active SmartCrash
  222.  
  223.     move.l    (sigf_REMOVED,pc),-(sp)    MyMes_RemovedSigMask
  224.     move.l    (sigf_INITOK,pc),-(sp)    MyMes_InitOkSigMask
  225.     move.l    (SigThisTask,pc),-(sp)    MyMes_SigTask
  226.     pea    MyMes_SIZEOF        MN_REPLYPORT:16, MN_LENGTH
  227.     clr.l    -(sp)            LN_NAME:16, MN_REPLYPORT:16
  228.     pea    MMTYPE_REMOVE<<8    LN_TYPE, LN_PRI, LN_NAME:16
  229.     clr.l    -(sp)            LN_PRED
  230.     clr.l    -(sp)            LN_SUCC
  231.     move.l    sp,a1
  232.     move.l    d0,a0            a0=MsgPort!
  233.     call    PutMsg
  234.     call    Permit
  235.     ; Wait subtask to exit
  236.     move.l    (sigf_INITOK,pc),d0
  237.     or.l    (sigf_REMOVED,pc),d0
  238.     call    Wait
  239.     lea    (MyMes_SIZEOF,sp),sp
  240.  
  241.     lea    (sRemoved,pc),a0
  242.     bsr    Printf
  243.     moveq    #RETURN_WARN,d7
  244.     bra    .cantinst
  245.  
  246.     ; Install SmartCrash to memory
  247.  
  248. .install    call    Permit
  249.     move.l    (DefTaskTrap,pc),d0
  250.     bne.b    .doinstall
  251.     lea    (sTrapUsed,pc),a0
  252.     bsr    Printf
  253.     bra    .cantinst
  254. .doinstall
  255.     lea    (GfxName,pc),a1
  256.     bsr    openlib
  257.     move.l    d0,_GfxBase
  258.  
  259.     move.l    (DosBase,pc),a6
  260.     move.l    #Template,d1
  261.     move.l    #ArgArray,d2
  262.     moveq    #0,d3
  263.     call    ReadArgs
  264.     move.l    d0,RDArgs
  265.     beq    .noargs
  266.  
  267.     move.l    (4).w,a6
  268.     move.l    (ArgArray+ARG_USEREQTOOLS*4,pc),d0
  269.     beq    .noreqtools
  270.  
  271.     lea    (ReqToolsName,pc),a1
  272.     moveq    #38,d0
  273.     call    OpenLibrary
  274.     move.l    d0,RTBase
  275.     beq.b    .noreqtools
  276.  
  277.     lea    (TAttr,pc),a4
  278.     move.w    #8,(ta_YSize,a4)    Default size
  279.     move.l    (ArgArray+ARG_RTFONTSIZE*4,pc),d0
  280.     beq.b    .nofsize
  281.     move.l    d0,a0
  282.     move.w    (2,a0),(ta_YSize,a4)
  283. .nofsize
  284.     move.l    (ArgArray+ARG_RTFONT*4,pc),d0
  285.     beq.b    .nofname
  286.     move.l    d0,a0
  287.     lea    (FontName,pc),a1
  288.     move.l    a1,(a4)            (ta_Name,a4)
  289.     moveq    #MAXFONTNAMELEN-1-1,d0
  290. .copy_fname    move.b    (a0)+,(a1)+
  291.     dbeq    d0,.copy_fname
  292.  
  293.     lea    (DiskFontName,pc),a1
  294.     moveq    #37,d0
  295.     call    OpenLibrary
  296.     tst.l    d0
  297.     beq.b    .no_dfb
  298.     move.l    d0,a6
  299.     move.l    a4,a0
  300.     call    OpenDiskFont
  301.     move.l    d0,FontBase
  302.     move.l    a6,a1
  303.     move.l    (4).w,a6
  304.     call    CloseLibrary
  305. .no_dfb
  306. .nofname
  307. .nofont
  308. .noreqtools
  309.     move.l    (SigThisTask,pc),SigTask
  310.  
  311.     move.l    #COPY_LEN,d0
  312.     moveq    #MEMF_PUBLIC,d1
  313.     call    AllocVec
  314.     move.l    d0,Copy
  315.     beq    .nomem
  316.  
  317.     lea    (COPY_START,pc),a0
  318.     move.l    (Copy,pc),a1
  319.     move.l    #COPY_LEN,d0
  320.     call    CopyMemQuick
  321.  
  322.     move.l    (Copy,pc),a4
  323.  
  324.     ; Fix TextAttr
  325.     move.l    (FontBase,pc),d0
  326.     beq.b    .nofix
  327.     lea    (FontName-COPY_START,a4),a0
  328.     move.l    a0,(TAttr+ta_Name-COPY_START,a4)
  329. .nofix
  330.     call    CacheClearU
  331.  
  332.     move.l    #2048,d0        Might call intuition
  333.     moveq    #100,d1            Priority 100
  334.     lea    (TaskName-COPY_START,a4),a0
  335.     lea    (TaskCode-COPY_START,a4),a1
  336.     ; a3=random
  337.     bsr    LaunchTask
  338.     beq.b    .terror
  339.  
  340.     ; Wait subtask status
  341.     move.l    (sigf_INITOK,pc),d0
  342.     or.l    (sigf_REMOVED,pc),d0
  343.     call    Wait
  344.     and.l    (sigf_INITOK,pc),d0
  345.     beq.b    .nortclose        <- Handles RTBase & Copy itself!
  346.  
  347.     moveq    #RETURN_OK,d7
  348.     lea    (sInstalled,pc),a0
  349.     bsr    Printf
  350.     bra.b    .nortclose
  351.  
  352. .terror    move.l    (Copy,pc),a1
  353.     call    FreeVec
  354. .nomem    move.l    (RTBase,pc),a1
  355.      call    CloseLibrary
  356. .nortclose    move.l    (DosBase,pc),a6
  357.     move.l    (RDArgs,pc),d1
  358.     call    FreeArgs
  359. .cantinst    cmp.w    #RETURN_WARN,d7
  360.     bls.b    .ok
  361.     lea    (sCantInstall,pc),a0
  362.     bsr    Printf
  363. .ok
  364. .nodos    move.l    (4).w,a6
  365.     move.l    (sigb_INITOK,pc),d0
  366.     call    FreeSignal
  367. .nosig2
  368.     move.l    (sigb_REMOVED,pc),d0
  369.     call    FreeSignal
  370. .nosig1
  371. .no37    move.l    d7,d0
  372.     rts
  373.  
  374.  
  375. .noargs    call    IoErr
  376.     move.l    d0,d1
  377.     lea    (.argerr,pc),a0
  378.     move.l    a0,d2
  379.     call    PrintFault
  380.     bra    .cantinst
  381. .argerr    dc.b    'argument error',0
  382.     CNOP    0,2
  383.  
  384.  
  385. Printf    move.l    a6,-(sp)
  386.     move.l    a0,d1
  387.     move.l    (DosBase,pc),a6
  388.     call    PutStr
  389.     move.l    (sp)+,a6
  390.     rts
  391.  
  392.  
  393. GetDefTraps    move.l    (TaskTrapCode,a6),d3
  394.  
  395.     move.l    (SigThisTask,pc),-(sp)
  396.     move.l    (sigf_INITOK,pc),-(sp)
  397.     move.l    sp,a3            Specialdata = {INITOK sigmask,SigThisTask}
  398.     move.l    #256,d0            Stack = 256 bytes
  399.     moveq    #10,d1            Priority = 10
  400.     sub.l    a0,a0            No special name
  401.     lea    (.proc,pc),a1
  402.     bsr    LaunchProc
  403.     move.l    (sigf_INITOK,pc),d0
  404.     call    Wait
  405.     move.l    (sp)+,d4
  406.     addq.l    #4,sp
  407.  
  408.     ; d3=TaskTrapCode
  409.     ; d4=ProcTrapCode
  410.  
  411.     move.l    (LN_NAME,a6),d0
  412.     move.l    #-$80000,d1
  413.     move.l    d1,d2
  414.     and.l    d1,d0
  415.     and.l    d3,d1
  416.     and.l    d4,d2
  417.     cmp.l    d0,d1
  418.     bne.b    .cantinstall
  419.     cmp.l    d0,d2
  420.     bne.b    .cantinstall
  421.  
  422.     move.l    d3,DefTaskTrap
  423.     move.l    d4,DefProcTrap
  424. .cantinstall    rts
  425.  
  426. .proc    move.l    (4).w,a6
  427.     sub.l    a1,a1
  428.     call    FindTask
  429.     move.l    d0,a2
  430.     move.l    (TC_Userdata,a2),a0
  431.     movem.l    (a0),d0/a1
  432.     move.l    (TC_TRAPCODE,a2),(a0)
  433.     jmp    (_LVOSignal,a6)
  434.     
  435.  
  436.     dc.b    '$VER: SmartCrash 1.3.0 (9.3.00)',10,0
  437.     dc.b    '$COPYRIGHT: '
  438. AboutMessage    dc.b    'SmartCrash 1.3.0 Copyright © 1995-2000 Harry "Piru" Sintonen.',10
  439.     dc.b    'All rights reserved. SmartCrash is freeware.',10,0
  440. DosName    dc.b    'dos.library',0
  441. GfxName    dc.b    'graphics.library',0
  442. DiskFontName    dc.b    'diskfont.library',0
  443. ReqToolsName    dc.b    'reqtools.library',0
  444. Template    dc.b    'RT=USEREQTOOLS/S,RTFONTNAME,RTFONTSIZE/N',0
  445. sInstalled    dc.b    'SmartCrash installed.',10,0
  446. sTrapUsed    dc.b    'TaskTrapCode is used by some other (similar) program.',10,0
  447. sCantInstall    dc.b    'Could not install SmartCrash.',10,0
  448. sRemoved    dc.b    'SmartCrash removed.',10,0
  449.  
  450.     CNOP    0,4
  451. COPY_START
  452.  
  453. ;  IN: d0.l=stacksize
  454. ;      d1.b=priority (-128 to 127)
  455. ;      a0.l=taskname
  456. ;      a1.l=initPC
  457. ;      a3.l=optional parameter (put to stack)
  458. ; OUT: d0.l=address of the new task or NULL, ccr set
  459. LaunchTask    movem.l    d1-d7/a0-a6,-(sp)
  460.     moveq    #0,d7
  461.     addq.l    #7,d0
  462.     and.w    #-8,d0
  463.     move.l    d0,d6
  464.     move.l    a0,a5
  465.     move.l    a1,a4
  466.     move.l    (4).w,a6
  467.     move.l    d6,-(sp)
  468.     pea    MEMF_PUBLIC|MEMF_CLEAR    Entry #1 (stack)
  469.     pea    (TC_SIZE).w
  470.     pea    MEMF_PUBLIC|MEMF_CLEAR    Entry #0 (TCB)
  471.     pea    (2).w            Number of entries (longword zeropadded)
  472.     lea    (-(LN_SIZE-2),sp),sp    Reserve space for list node (-2 = padding...)
  473.     move.l    sp,a0
  474.     call    AllocEntry
  475.     lea    ((LN_SIZE-2)+(5*4),sp),sp
  476.     tst.l    d0
  477.     bmi.b    .exit
  478.     move.l    d0,a0
  479.     move.l    (ML_ME+0*ME_SIZE,a0),a1
  480.     lea    (TC_MEMENTRY,a1),a2
  481.     NEWLIST    a2
  482.     movem.l    a0-a1/d0-d1,-(sp)
  483.     move.l    a0,a1
  484.     move.l    a2,a0
  485.     call    AddHead
  486.     movem.l    (sp)+,a0-a1/d0-d1
  487.     move.l    (ML_ME+1*ME_SIZE,a0),a2
  488.     move.l    a2,(TC_SPLOWER,a1)
  489.     add.l    d6,a2
  490.     move.l    a2,(TC_SPUPPER,a1)
  491.     move.l    a3,-(a2)
  492.     move.l    a2,(TC_SPREG,a1)
  493.     move.b    #NT_TASK,(LN_TYPE,a1)
  494.     move.b    (3,sp),(LN_PRI,a1)    d1 is topmost in stack...
  495.     move.l    a5,(LN_NAME,a1)
  496.     ;move.b    #TF_ETASK,(TC_FLAGS,a1)
  497.     move.l    a4,a2
  498.     sub.l    a3,a3
  499.     move.l    a1,d7
  500.     call    AddTask            Can't fail, really.
  501.     cmp.l    d0,d7
  502.     beq.b    .exit
  503.  
  504.     ; So, it DID fail after all. Damn it, now we need to
  505.     ; free everything ourself.
  506.     move.l    d7,a0
  507.     move.l    (TC_MEMENTRY,a0),a0
  508.     call    FreeEntry
  509.     moveq    #0,d7
  510.  
  511. .exit    move.l    d7,d0
  512.     movem.l    (sp)+,d1-d7/a0-a6
  513.     rts
  514.  
  515. ;  IN: d0=stacksize
  516. ;      d1=priority (-128 to 127)
  517. ;      a0=procname (can be NULL)
  518. ;      a1=initPC
  519. ;      a3=optional parameter (Will be put to TC_Userdata)
  520. ; OUT: d0.l=address of the new process or NULL, ccr set
  521. LaunchProc    movem.l    d1-d7/a0-a6,-(sp)
  522.     move.l    sp,a4
  523.     addq.l    #7,d0
  524.     and.w    #-8,d0
  525.     move.l    (DosBase,pc),a5
  526.     move.l    (4).w,a6
  527.     clr.l    -(sp)            TAG_END
  528.     move.l    d0,-(sp)
  529.     pea    NP_StackSize
  530.     move.l    d1,-(sp)
  531.     pea    NP_Priority
  532.     move.l    a0,d0
  533.     beq.b    .noname
  534.     move.l    a0,-(sp)
  535.     pea    NP_Name
  536. .noname    move.l    a1,-(sp)
  537.     pea    NP_Entry
  538.     pea    (-1).w
  539.     pea    NP_CopyVars
  540.     move.l    sp,d1
  541.     call    Forbid
  542.     exg    a5,a6
  543.     call    CreateNewProc
  544.     tst.l    d0
  545.     beq.b    .error
  546.     move.l    d0,a0
  547.     move.l    a3,(TC_Userdata,a0)
  548. .error    exg    a5,a6
  549.     call    Permit
  550.     move.l    a4,sp
  551.     tst.l    d0
  552.     movem.l    (sp)+,d1-d7/a0-a6
  553.     rts
  554.  
  555.  
  556. openlib    moveq    #37,d0
  557.     call    OpenLibrary
  558.     move.l    d0,-(sp)
  559.     move.l    d0,a1
  560.     call    CloseLibrary
  561.     move.l    (sp)+,d0
  562.     rts
  563.  
  564.  
  565. TaskCode    lea    (DT,pc),a5
  566.     move.l    (4).w,a6
  567.     move.l    a6,(_ExecBase-DT,a5)
  568.     sub.l    a1,a1
  569.     call    FindTask
  570.     move.l    d0,(_ThisTask-DT,a5)
  571.  
  572.     lea    (CrashData,pc),a0
  573.     IFD    HACKSEMAPHORE
  574.     clr.l    (a0)
  575.     ELSE
  576.     call    InitSemaphore
  577.     ENDC
  578.  
  579.     moveq    #-1,d0
  580.     call    AllocSignal
  581.     move.l    d0,(sigb_EXITSUB-DT,a5)
  582.     bmi    .nosig1
  583.     moveq    #1,d1
  584.     lsl.l    d0,d1
  585.     move.l    d1,(sigf_EXITSUB-DT,a5)
  586.  
  587.     lea    (IntuiName,pc),a1
  588.     bsr    openlib
  589.     move.l    d0,(IntuiBase-DT,a5)
  590.  
  591.     call    CreateMsgPort
  592.     move.l    d0,(MsgPort-DT,a5)
  593.     beq    .noport
  594.     move.l    d0,a1
  595.     lea    (PortName,pc),a0
  596.     move.l    a0,(LN_NAME,a1)
  597.     move.b    #-126,(LN_PRI,a1)
  598.  
  599.     call    Forbid
  600.     lea    (PortName,pc),a1    check for race condition
  601.     call    FindPort        (if two smartcrashes were initializing
  602.     tst.l    d0            at the same time)
  603.     bne    .race_condition
  604.  
  605.     move.l    (MsgPort-DT,a5),a1
  606.     call    AddPort
  607.     ; PatchControl installed?
  608.     lea    (SetManPortName,pc),a1
  609.     call    FindPort
  610.     call    Permit
  611.     move.l    d0,(HavePatchCtrl-DT,a5)
  612.  
  613.     moveq    #AllocPatch_SIZEOF,d0
  614.     moveq    #MEMF_PUBLIC,d1
  615.     call    AllocMem
  616.     move.l    d0,(RecMem-DT,a5)
  617.     beq    .no_recmem
  618.     move.l    d0,a1
  619.     moveq    #TrapEntry-AllocPatch,d1
  620.     add.l    d0,d1
  621.     move.l    d1,(TrapEntryPtr-DT,a5)
  622.     move.l    a1,-(sp)
  623.     lea    (AllocPatch,pc),a0
  624.     moveq    #AllocPatch_SIZEOF,d0
  625.     call    CopyMem
  626.     move.l    (sp)+,a0
  627.     lea    (AddTaskCode,pc),a1
  628.     move.l    a1,(JMPADDROFFS,a0)
  629.  
  630.     ; Special handler for 68000
  631.     lea    (NewHandler000,pc),a1
  632.     btst    #AFB_68010,(AttnFlags+1,a6)
  633.     beq.b    .is_68000
  634.     ; Have 68010 or better so use simpler handler:
  635.     lea    (NewHandler010,pc),a1
  636. .is_68000    move.l    a1,(TrapProc-AllocPatch,a0)
  637.     move.l    a1,(TrapTask-AllocPatch,a0)
  638.  
  639.     moveq    #_jmppos-AllocPatch,d0
  640.     add.l    a0,d0
  641.     move.w    #_LVOAddTask,a0
  642.     move.l    a6,a1
  643.     call    Forbid
  644.     call    SetFunction
  645.     move.l    d0,(_ATC_orig-DT,a5)
  646.  
  647.     ; Change execbase TaskTrapCode
  648.     move.l    (TrapEntryPtr,pc),(TaskTrapCode,a6)
  649.  
  650.     ; Change ready/wait task's TrapCode
  651.     move.l    (DefProcTrap,pc),a1    a1=proc trapcode
  652.     move.l    (DefTaskTrap,pc),a2    a2=task trapcode
  653.     move.l    (TrapEntryPtr,pc),d2    d2=our new trap entry (proc)
  654.     move.l    d2,d3            d3=our new trap entry (task)
  655.     move.l    (TaskReady,a6),a0
  656.     bsr    .ChangeTrapCode
  657.     move.l    (TaskWait,a6),a0
  658.     bsr    .ChangeTrapCode
  659.  
  660.     call    CacheClearU
  661.     call    Permit
  662.  
  663.     move.l    (sigf_INITOK,pc),d0    Notify about successful
  664.     bsr    NotifySigTask        install.
  665.  
  666.     ; SmartCrash.manager main:
  667.  
  668. .mainloop    move.l    (MsgPort,pc),a0
  669.     call    WaitPort
  670. .moremsg    move.l    (MsgPort,pc),a0
  671.     call    GetMsg
  672.     tst.l    d0
  673.     beq.b    .mainloop
  674.  
  675.     move.l    d0,a0
  676.     move.b    (MyMes_Type,a0),d0
  677.     cmp.b    #MMTYPE_REMOVE,d0
  678.     beq    .remove
  679.     cmp.b    #MMTYPE_REPORT,d0
  680.     bne.b    .moremsg
  681.  
  682.     ; Launch new requester task (SubCode)
  683.  
  684.     move.l    (_ThisTask,pc),a3    Pass parent task
  685.     move.l    #4096+10240,d0        Must have 2k for SegTrackerInfo
  686.     moveq    #3,d1            Priority 3
  687.     lea    (SubName,pc),a0
  688.     lea    (SubCode,pc),a1
  689.     addq.l    #1,(SubTaskCnt-DT,a5)
  690.     bsr    LaunchTask
  691.     bne.b    .moremsg        .taskok
  692.  
  693.     ; If no task could be created,
  694.     ; fallback to an alert.
  695.     ;
  696.     ; This could be a bit bugged.
  697.  
  698. ;;    call    Forbid
  699.  
  700.     lea    (CrashData,pc),a4
  701.     lea    (-5*4,sp),sp        -1*4 for clr.b (4*4+1,a1)...
  702.  
  703.     move.l    sp,a1
  704.     move.b    #'"',d2
  705.     move.l    (CD_Task,a4),a0        Copy taskname:
  706.     moveq    #16-1,d0
  707.     move.l    (LN_NAME,a0),d1
  708.     beq.b    .a_dopad
  709.     move.l    d1,a0
  710. .a_strcopy    move.b    (a0)+,(a1)+
  711.     dbeq    d0,.a_strcopy
  712.     tst.b    -(a1)            Pad name with spaces:
  713.     bne.b    .a_notzero
  714. .a_dopad    move.b    d2,(a1)+
  715. .a_pad    move.b    #' ',(a1)+
  716.     subq.w    #1,d0
  717.     bpl.b    .a_pad
  718. .a_notzero    move.b    d2,(a1)+        <- Doesn't matter!
  719.     clr.b    (a1)
  720.  
  721.     move.l    sp,-(sp)
  722.     move.l    (CD_Task,a4),-(sp)
  723.     move.l    (CD_ProgramCounter,a4),-(sp)
  724.     move.l    (CD_ExceptionNumber,a4),-(sp)
  725.     bset    #7,(sp)
  726.     lea    (Alert01Fmt,pc),a0
  727.     move.l    sp,a1
  728.     lea    (PutChar,pc),a2
  729.     lea    (Alert01Buf,pc),a3
  730.     call    RawDoFmt
  731.     lea    (5*4+4*4,sp),sp
  732.  
  733.     move.l    a4,a0            Steal & release semaphore
  734.     IFD    HACKSEMAPHORE
  735.     clr.l    (a0)
  736.     ELSE
  737.     move.l    (_ThisTask,pc),(SS_OWNER,a0)    <- HACK
  738.     call    ReleaseSemaphore
  739.     ENDC
  740. ;;    call    Permit
  741.  
  742.     move.l    a6,-(sp)
  743.     move.l    (IntuiBase,pc),a6
  744.     moveq    #-66,d0            deadend
  745.     lea    (Alert01,pc),a0
  746.     moveq    #0,d1
  747.     move.b    (Alert01_len,pc),d1
  748.     cmp.w    #39,(LIB_VERSION,a6)
  749.     blo.b    .old_alert
  750.     move.w    #30*50,a1
  751.     call    TimedDisplayAlert
  752.     bra.b    .skip_old
  753. .old_alert    call    DisplayAlert
  754. .skip_old    move.l    (sp)+,a6
  755.     subq.l    #1,(SubTaskCnt-DT,a5)
  756.     bra    .moremsg
  757.  
  758. ;  IN: a1=DefProcTrap
  759. ;      a2=DefTaskTrap
  760. ;      d2=proc TrapEntryPtr
  761. ;      d3=task TrapEntryPtr
  762. .ChangeTrapCode
  763. .ct_loop    move.l    (a0),d0
  764.     beq.b    .ct_done
  765.     move.l    (TC_TRAPCODE,a0),d1
  766.     cmp.b    #NT_PROCESS,(LN_TYPE,a0)
  767.     bne.b    .ct_task
  768.     cmp.l    a1,d1
  769.     beq.b    .ct_fix
  770.  
  771. .ct_tryold
  772.     ; It's a custom TC_TRAPCODE, so check for old
  773.     ; incarnation of ourself...
  774.  
  775.     move.l    d1,a3
  776.     cmp.l    #SMARTCRASH13_ID,(-SC13IDPOS,a3)
  777.     beq.b    .ct_fix
  778.     bra.b    .ct_skip
  779.  
  780. .ct_task    cmp.l    a2,d1
  781.     bne.b    .ct_tryold
  782. .ct_fix    move.l    d3,d1            task TrapEntryPtr
  783.     cmp.b    #NT_PROCESS,(LN_TYPE,a0)
  784.     bne.b    .ct_do
  785.     move.l    d2,d1            proc TrapEntryPtr
  786. .ct_do    move.l    d1,(TC_TRAPCODE,a0)
  787. .ct_skip
  788.     move.l    d0,a0
  789.     bra.b    .ct_loop
  790. .ct_done    rts
  791.  
  792.  
  793.  
  794.     ; SigTask asked us to quit...
  795.  
  796. .remove    move.l    (MyMes_SigTask,a0),(SigTask-DT,a5)
  797.     move.l    (MyMes_InitOkSigMask,a0),(sigf_INITOK-DT,a5)
  798.     move.l    (MyMes_RemovedSigMask,a0),(sigf_REMOVED-DT,a5)
  799.  
  800.     call    Forbid
  801.  
  802.     ; Restore TC_TRAPCODE for every task possible:
  803.     move.l    (TrapEntryPtr,pc),a1    a1=our new trap entry
  804.     move.l    a1,a2
  805.     move.l    (DefProcTrap,pc),d2    d2=proc trapcode
  806.     move.l    (DefTaskTrap,pc),d3    d3=task trapcode
  807.     move.l    (TaskReady,a6),a0
  808.     bsr    .ChangeTrapCode
  809.     move.l    (TaskWait,a6),a0
  810.     bsr    .ChangeTrapCode
  811.  
  812.     ; Restore original execbase TaskTrapCode
  813.     move.l    (DefTaskTrap,pc),(TaskTrapCode,a6)
  814.  
  815.     ; Modify TrapEntry such way it will redirect all
  816.     ; traps to original routine.
  817.     move.l    (RecMem,pc),a3
  818.     move.l    (_ATC_orig,pc),(JMPADDROFFS,a3)
  819.     move.l    (DefTaskTrap,pc),(TrapTask-AllocPatch,a3)
  820.     move.l    (DefProcTrap,pc),(TrapProc-AllocPatch,a3)
  821.  
  822.     ; Remove AddTask patch if possible
  823.     move.w    #_LVOAddTask,a0
  824.     ; If PatchControl is installed force remove
  825.     tst.l    (HavePatchCtrl-DT,a5)
  826.     bne.b    .force_remove
  827.     move.l    2(a6,a0.l),a1
  828.     subq.l    #_jmppos-AllocPatch,a1
  829.     cmp.l    a3,a1
  830.     bne.b    .cant_remove
  831. .force_remove    move.l    (_ATC_orig,pc),d0
  832.     move.l    a6,a1
  833.     call    SetFunction
  834. .cant_remove    call    CacheClearU
  835.     call    Permit
  836.  
  837. .no_recmem
  838.     lea    (CrashData,pc),a0
  839.     IFD    HACKSEMAPHORE
  840. .wait    tst.l    (a0)
  841.     bne.b    .wait
  842.     addq.l    #1,(a0)
  843.     ELSE
  844.     call    ObtainSemaphore
  845.     ENDC
  846.  
  847. .try_exit    tst.l    (SubTaskCnt-DT,a5)    Wait all subtasks to quit.
  848.     beq.b    .no_more_subtasks
  849.     move.l    (sigf_EXITSUB,pc),d0
  850.     call    Wait
  851.     bra.b    .try_exit
  852. .no_more_subtasks
  853.  
  854. .no_mem    move.l    (MsgPort,pc),a1
  855.     call    Forbid
  856.     call    RemPort
  857.     call    Permit
  858. .cleanloop    move.l    (MsgPort,pc),a0
  859.     call    GetMsg
  860.     tst.l    d0
  861.     bne.b    .cleanloop
  862.  
  863. .delport    move.l    (MsgPort,pc),a0
  864.     call    DeleteMsgPort
  865.  
  866. .noport    move.l    (sigb_EXITSUB,pc),d0
  867.     call    FreeSignal
  868.  
  869. .nosig1    move.l    (_ExecBase,pc),a6
  870.     move.l    (RTBase,pc),a1
  871.     call    CloseLibrary
  872.  
  873.     move.l    a6,-(sp)
  874.     move.l    (_GfxBase,pc),a6
  875.     lea    (FontBase,pc),a0
  876.     move.l    (a0),d0
  877.     beq.b    .no_rtfont
  878.     clr.l    (a0)
  879.     move.l    d0,a1
  880.     call    CloseFont
  881. .no_rtfont    move.l    (sp)+,a6
  882.  
  883.     lea    (CrashData,pc),a0
  884.     IFD    HACKSEMAPHORE
  885.     clr.l    (a0)
  886.     ELSE
  887.     call    ReleaseSemaphore
  888.     ENDC
  889.  
  890.     move.l    (sigf_REMOVED,pc),d0    Signal mask
  891.     call    Forbid            Prevent race conditions
  892.     bsr.b    NotifySigTask
  893.  
  894.     lea    (COPY_START,pc),a1    FreeVec self
  895.     jmp    (_LVOFreeVec,a6)    & terminate
  896.  
  897.  
  898. .race_condition    call    Permit
  899.     bra    .delport
  900.  
  901.  
  902. PutChar    move.b    d0,(a3)+
  903. nm_rts    rts
  904.  
  905.  
  906.  
  907. NotifySigTask    lea    (SigTask,pc),a0
  908.     move.l    (a0),a1
  909.     clr.l    (a0)
  910.     move.l    a1,d1
  911.     beq.b    nm_rts
  912.     jmp    (_LVOSignal,a6)
  913.  
  914.  
  915.     ; If can't get signal just suspend.
  916. sc_nosignal    addq.l    #4,sp
  917. sc_steal    move.l    a5,a0            Steal & release semaphore
  918.     IFD    HACKSEMAPHORE
  919.     clr.l    (a0)
  920.     rts
  921.     ELSE
  922.     move.l    d6,(SS_OWNER,a0)    <- HACK
  923.     jmp    (_LVOReleaseSemaphore,a6)
  924.     ENDC
  925.  
  926. SubCode    move.l    (_ExecBase,pc),a6
  927.     sub.l    a1,a1
  928.     call    FindTask
  929.     move.l    d0,d6
  930.  
  931.     ; This thing prevents (possible) recursion if SubCode
  932.     ; itself should fail for some reason.
  933.     move.l    d0,a0
  934.     move.l    (DefTaskTrap,pc),(TC_TRAPCODE,a0)
  935.  
  936.     lea    (CrashData,pc),a5
  937.  
  938.     ; Allocate SKIPPED signal that is used to signal
  939.     ; when it is ok to quit SubCode after Skip. This signal
  940.     ; is ONLY for the local use, ie. even it is stored to
  941.     ; global structure only Trap_UserPart may use it.
  942.  
  943.     moveq    #-1,d0
  944.     call    AllocSignal
  945.     move.l    d0,-(sp)
  946.     bmi.b    sc_nosignal
  947.     moveq    #1,d1
  948.     lsl.l    d0,d1
  949.     move.l    d1,(CD_sigf_SKIPPED,a5)
  950.  
  951.     move.l    sp,d7
  952.  
  953.     move.l    (CD_UserStackPtr,a5),d0
  954.     btst    #13-8,(CD_StatusRegister,a5)
  955.     beq.b    .is_user
  956.     move.l    (CD_SuperStackPtr,a5),d0
  957. .is_user    move.l    d0,(CD_StackPtr,a5)
  958.  
  959.     ; force stack even before stackframe copy, prevent problems
  960.     ; with 68000 and allow SegTrackerInfo stack scan work.
  961.     and.w    #$FFFE,d0
  962.     move.l    d0,a0
  963.     lea    (CD_StackFrame,a5),a1
  964.     moveq    #16,d0
  965. .copy    move.l    (a0)+,(a1)+
  966.     subq.l    #1,d0
  967.     bne.b    .copy
  968.  
  969.     lea    (CD_ExceptionNumber,a5),a0
  970.     move.l    (a0)+,d0
  971.     lea    (sKnown,pc),a1
  972.     lea    (ExceptionTable,pc),a2
  973.     move.l    d0,d1
  974.     lea    (CD_TrapNumber,a5),a3
  975.     add.l    d1,d1
  976.     clr.b    (a3)
  977.     move.w    (a2,d1.l),d1
  978.     cmp.w    #$3A,d0
  979.     bhi.b    .str_not_ok
  980.     cmp.w    #$2F,d0
  981.     bhi.b    .not_trapn
  982.     cmp.w    #$1F,d0
  983.     bls.b    .not_trapn
  984.     add.w    #'0'-$20,d0
  985.     cmp.w    #'9',d0
  986.     bls.b    .hex_ok
  987.     addq.w    #'@'-'9',d0
  988. .hex_ok    move.b    d0,(a3)
  989. .not_trapn
  990.     add.w    d1,a2
  991.     not.w    d1
  992.     bne.b    .str_ok
  993. .str_not_ok    addq.l    #NullStr-sKnown,a1
  994.     move.l    a1,a2
  995. .str_ok    move.l    a1,(a0)+        CD_ExceptionStr1
  996.     move.l    a2,(a0)+        CD_ExceptionStr2
  997.  
  998.     move.l    (CD_Task,a5),a0
  999.     moveq    #sTask-sTask,d0
  1000.     moveq    #0,d4            Default pubscreen for tasks!
  1001.     cmp.b    #NT_PROCESS,(LN_TYPE,a0)
  1002.     bne.b    .task
  1003.     move.l    (pr_WindowPtr,a0),d4
  1004.     move.l    #$80000001,d1        Some sanity check for window
  1005.     and.l    d4,d1
  1006.     beq.b    .winok
  1007.     moveq    #0,d4
  1008. .winok
  1009.     move.l    (pr_CLI,a0),d1
  1010.     beq.b    .process
  1011.     lsl.l    #2,d1
  1012.     move.l    d1,a1
  1013.     move.l    (cli_CommandName,a1),-(sp)
  1014.     move.l    (pr_TaskNum,a0),-(sp)
  1015.     lea    (CLIFmt,pc),a0
  1016.     move.l    sp,a1
  1017.     lea    (-64,sp),sp
  1018.     lea    (PutChar,pc),a2
  1019.     move.l    sp,a3
  1020.     call    RawDoFmt
  1021.     move.l    sp,a1
  1022.     moveq    #sCommand-sTask,d0
  1023.     bra.b    .done
  1024.  
  1025. .process    moveq    #sProcess-sTask,d0
  1026. .task    move.l    (LN_NAME,a0),a1
  1027. .done
  1028.     lea    (sTask,pc),a0
  1029.     add.l    d0,a0
  1030.     lea    (CD_TaskType,a5),a4
  1031.     move.l    a0,(a4)+        CD_TaskType
  1032.     move.l    a1,(a4)+        CD_TaskName
  1033.  
  1034.     ; SegTracker info to stack:
  1035.     ; stack usage varies, but theoritical maximum usage would be:
  1036.     ; 41 * ( 43 + 28 ) = 2911 bytes
  1037.     ; ALL possible 41 SegTracker hits,
  1038.     ; 43 bytes of constant string + max. 26 byte segment name,
  1039.     ; but in real life this can newer happen, so 2k is enough.
  1040.     lea    (-2048,sp),sp
  1041.     move.l    sp,(a4)            CD_SegTrackerInfo
  1042.     move.l    sp,a3
  1043.     bsr    SegTrackerInfo
  1044.  
  1045.     ; GadgetFmt argarray to stack
  1046.  
  1047.     lea    (UnderlStr,pc),a0
  1048.     move.l    (RTBase,pc),d0
  1049.     bne.b    .is_rt
  1050.     addq.l    #1,a0
  1051. .is_rt    moveq    #NUMSCGADGETS,d0
  1052. .do_under    move.l    a0,-(sp)
  1053.     subq.l    #1,d0
  1054.     bne.b    .do_under
  1055.  
  1056.     ; BodyFmt argarray to stack
  1057.  
  1058.     lea    (CD_CD_END,a5),a0    Copy semaphore data to *local*
  1059.     moveq    #(CD_CD_END-CD_CD)/4,d0    stack area. After this we can
  1060. .copy_cd    move.l    -(a0),-(sp)        release the semaphore.
  1061.     subq.l    #1,d0
  1062.     bne.b    .copy_cd
  1063.  
  1064.     bsr    sc_steal        Steal & release semaphore
  1065.  
  1066.     ;lea    (CD_TrapNumber-CD_CD,sp),a0
  1067.     ;move.l    a0,(CD_ExceptionStr3-CD_CD,sp)
  1068.     move.l    sp,(CD_ExceptionStr3-CD_CD,sp)        'Trap #<n>' string ptr
  1069.     lea    (CD_ExceptionNumber-CD_CD,sp),a3    AgrList for requester
  1070.  
  1071.     move.l    (RTBase,pc),d0
  1072.     bne.b    .use_rtreq
  1073.  
  1074.     pea    (GadgetFmt,pc)
  1075.     pea    (BodyFmt,pc)
  1076.     pea    (WindowTitle,pc)
  1077.     clr.l    -(sp)
  1078.     pea    (EasyStruct_SIZEOF).w
  1079.  
  1080. .redo_easyreq    move.l    d4,a0            Window ptr
  1081.     move.l    sp,a1            easyStruct
  1082.     sub.l    a2,a2            IDCMP_ptr (may be null)
  1083. ;        a3            ArgList
  1084.     move.l    (IntuiBase,pc),a6
  1085.     call    EasyRequestArgs
  1086.     bra.b    .handle_result
  1087.  
  1088. .use_rtreq    clr.l    -(sp)            TAG_END
  1089.     move.l    d4,-(sp)
  1090.     pea    RT_Window
  1091.     pea    (REQPOS_POINTER).w
  1092.     pea    RT_ReqPos
  1093.     pea    ('_').w
  1094.     pea    RT_Underscore
  1095.     pea    (WindowTitle,pc)
  1096.     pea    RTEZ_ReqTitle
  1097.     ;pea    (EZREQF_NORETURNKEY|EZREQF_LAMIGAQUAL).w
  1098.     pea    (EZREQF_LAMIGAQUAL).w
  1099.     pea    RTEZ_Flags
  1100.     move.l    (FontBase,pc),d0
  1101.     beq.b    .nofont
  1102.     pea    (TAttr,pc)
  1103.     pea    RT_TextAttr
  1104. .nofont
  1105. .redo_rtreq    lea    (BodyFmt,pc),a1
  1106.     lea    (GadgetFmt,pc),a2
  1107.     move.l    a3,a4
  1108.     sub.l    a3,a3
  1109.     move.l    sp,a0
  1110.     move.l    (RTBase,pc),a6
  1111.     call    rtEZRequestA
  1112.     move.l    a4,a3
  1113.  
  1114. .handle_result
  1115.     move.l    (_ExecBase,pc),a6
  1116.     move.l    (CD_Task-CD_ExceptionNumber,a3),a4    a4=crashed_task
  1117.     move.l    d6,(CD_Task-CD_ExceptionNumber,a3)    sigtask (SubCode) to CD_Task
  1118.  
  1119. ;;    bra    Debug_Reset        If unknown gadget
  1120.  
  1121.     add.l    d0,d0
  1122.     move.w    .tab(pc,d0.l),d0
  1123.     jmp    .tab(pc,d0.w)
  1124.  
  1125. .tab    dc.w    .exit_suspend-.tab    0 GADG_SUSPEND
  1126.     dc.w    .exit_skip-.tab        1 GADG_SKIP
  1127.     dc.w    .exit_remove-.tab    2 GADG_REMOVE
  1128.     dc.w    .exit_exit-.tab        3 GADG_EXIT
  1129.     dc.w    .exit_debug-.tab    4 GADG_DEBUG
  1130.     dc.w    .exit_reboot-.tab    5 GADG_REBOOT
  1131.     dc.w    .exit_jmp-.tab        6 GADG_JMP
  1132.     dc.w    .exit_rts-.tab        7 GADG_RTS
  1133.  
  1134. .exit_debug    moveq    #0,d0
  1135.     call    Debug
  1136. .redo_req    move.l    a4,(CD_Task-CD_ExceptionNumber,a3)    Restore the orig. CD_Task
  1137.     move.l    (RTBase,pc),d0
  1138.     beq    .redo_easyreq
  1139.     bra.b    .redo_rtreq
  1140.  
  1141. .exit_reboot    move.l    (_GfxBase,pc),a6
  1142.     sub.l    a1,a1
  1143.     call    LoadView
  1144.     call    WaitTOF
  1145.     call    WaitTOF
  1146.     move.l    (_ExecBase,pc),a6
  1147.     jmp    (_LVOColdReboot,a6)
  1148.  
  1149. .exit_skip    ; Wake task to skip failed instruction
  1150.     move.w    #ACTION_SKIP,(CD_Action-CD_ExceptionNumber,a3)
  1151. .skipkind    move.l    (TC_TRAPDATA,a4),(CD_PrevTRAPDATA-CD_ExceptionNumber,a3)
  1152.     move.l    a3,(TC_TRAPDATA,a4)    Pass stack version of CD,
  1153.     moveq    #1<<WAKE_SIGNAL,d0    TC_TRAPDATA = ptr to CD_ExceptionNumber
  1154.     or.l    d0,(TC_SIGWAIT,a4)
  1155.     move.l    a4,a1
  1156.     IFD    FIXED_SKIPPED_SIGNAL
  1157.     call    Signal
  1158.     move.l    #1<<FIXED_SKIPPED_SIGNAL,d0    Wait until task has skipped
  1159.     call    Wait
  1160.     ELSE
  1161.     ; *MUST* get it before Signal call!
  1162.     move.l    (CD_sigf_SKIPPED-CD_ExceptionNumber,a3),-(sp)
  1163.     call    Signal            must not use a3 anymore!
  1164.     move.l    (sp)+,d0
  1165.     call    Wait
  1166.     ENDC
  1167.     bra    .exit
  1168.  
  1169.  
  1170. .exit_rts    ; jump to rts
  1171.     lea    (.rts,pc),a0
  1172.     move.l    a0,(CD_ProgramCounter-CD_ExceptionNumber,a3)
  1173. .actjmp    move.w    #ACTION_JMP,(CD_Action-CD_ExceptionNumber,a3)
  1174.     bra.b    .skipkind
  1175.  
  1176.  
  1177. .exit_jmp    ; Put up number requester to query new program counter.
  1178.     ; Put result to CD_ProgramCounter.
  1179.  
  1180.     IFGT    0
  1181.     move.l    (RTBase,pc),d0
  1182.     beq.b    .no_rt
  1183.     move.l    d0,a6
  1184.     move.l    sp,d5
  1185.     clr.l    -(sp)
  1186.     move.l    d4,-(sp)
  1187.     pea    RT_Window
  1188.     pea    (REQPOS_POINTER).w
  1189.     pea    RT_ReqPos
  1190.     move.l    (FontBase,pc),d0
  1191.     beq.b    .nofont2
  1192.     pea    (TAttr,pc)
  1193.     pea    RT_TextAttr
  1194. .nofont2    move.l    sp,a0
  1195. ;;    lea    (CD_ProgramCounter-CD_ExceptionNumber,a3),a1
  1196.     lea    (.title,pc),a2
  1197.     sub.l    a3,a3
  1198. ;    call    rtGetStringA
  1199.     moveq    #0,d0
  1200.     move.l    d5,sp
  1201. .no_rt
  1202.     ENDC
  1203.  
  1204.     lea    (CD_ProgramCounter-CD_ExceptionNumber,a3),a0
  1205.     lea    (.title,pc),a1
  1206.     moveq    #RLF_ALLOWHEX|RLF_INITHEX|RLF_UNSIGNED|RLF_SHOWDEF|RLF_FOLLOWMOUSE|RLF_ESCISRETURN,d0
  1207.     bsr    RequestLong
  1208.     tst.l    d0
  1209.     beq    .redo_req        User cancelled, redo the requester
  1210.     ; User entered something so jump in!
  1211.     bra.b    .actjmp
  1212.  
  1213. .title    dc.b    'Jump to...',0
  1214.     CNOP    0,2
  1215.  
  1216.  
  1217. .exit_exit    cmp.b    #NT_PROCESS,(LN_TYPE,a4)
  1218.     bne.b    .exit_task
  1219.  
  1220.     ; Wake task for return with orig. stack:
  1221.     move.w    #ACTION_EXIT,(CD_Action-CD_ExceptionNumber,a3)
  1222.     move.l    (TC_TRAPDATA,a4),(CD_PrevTRAPDATA-CD_ExceptionNumber,a3)
  1223.     move.l    a3,(TC_TRAPDATA,a4)    Pass stack version of CD,
  1224.     moveq    #1<<WAKE_SIGNAL,d0    TC_TRAPDATA = ptr to CD_ExceptionNumber
  1225.     or.l    d0,(TC_SIGWAIT,a4)
  1226.     move.l    a4,a1
  1227.     call    Signal
  1228.     bra.b    .exit
  1229.  
  1230.  
  1231. .exit_remove    bsr.b    .closewindows
  1232.     ;call    Forbid
  1233.     cmp.b    #NT_PROCESS,(LN_TYPE,a4)
  1234.     bne.b    .exit_task
  1235.     or.w    #PRF_FREESEGLIST|PRF_FREECURRDIR|PRF_CLOSEINPUT|PRF_CLOSEOUTPUT|PRF_FREEARGS,(pr_Flags+2,a4)
  1236.     move.l    (pr_CLI,a4),d0
  1237.     beq.b    .not_cli
  1238.  
  1239.     ; !!
  1240.     ; should remove this CLI from dos cli list!
  1241.  
  1242.     clr.l    (pr_CLI,a4)
  1243.     and.w    #~(PRF_FREESEGLIST|PRF_FREECLI),(pr_Flags+2,a4)
  1244.     lsl.l    #2,d0
  1245.     move.l    d0,a3            Specialdata=CLI sturucture
  1246.     move.l    #4096,d0        Stack=4K
  1247.     moveq    #10,d1            Priority=10
  1248.     sub.l    a0,a0            No special name
  1249.     lea    (_DoSomeDos,pc),a1
  1250.     bsr    LaunchProc
  1251. .not_cli
  1252. .exit_task    move.l    (_ExecBase,pc),a6
  1253. ;;;    clr.l    (TC_ExitCode,a4)
  1254.     move.l    a4,a1
  1255.     call    RemTask            Fall thru to .exit!
  1256.  
  1257.  
  1258. .exit_suspend
  1259. .exit    move.l    (_ExecBase,pc),a6
  1260.     move.l    d7,sp
  1261.     move.l    (sp)+,d0
  1262.     call    FreeSignal
  1263.     lea    (SubTaskCnt,pc),a0
  1264.     move.l    (4,sp),a1        a1=sigtask (parent task)
  1265.     move.l    (sigf_EXITSUB,pc),d0    d0=sigmask
  1266.     call    Forbid            Forbid task scheduling
  1267.     subq.l    #1,(a0)
  1268.     jmp    (_LVOSignal,a6)        Signal & terminate
  1269.  
  1270.  
  1271.  
  1272. ;  IN: a4=task (or a process)
  1273. .closewindows    movem.l    d7/a2-a3/a5-a6,-(sp)
  1274.     move.l    (IntuiBase,pc),a6
  1275.  
  1276.     clr.l    -(sp)            array terminator
  1277.  
  1278.     moveq    #0,d0
  1279.     call    LockIBase
  1280.     move.l    d0,d7
  1281.  
  1282.     move.l    (ib_FirstScreen,a6),a5
  1283. .cw_sloop
  1284.     move.l    (sc_FirstWindow,a5),a3
  1285. .cw_wloop
  1286.     move.l    (wd_UserPort,a3),a0
  1287.     cmp.l    (MP_SIGTASK,a0),a4
  1288.     bne.b    .cw_nomatch
  1289.  
  1290.     move.l    a3,-(sp)        add window to array of windows to close
  1291. .cw_nomatch
  1292.     move.l    (a3),d0
  1293.     move.l    d0,a3
  1294.     bne.b    .cw_wloop
  1295.  
  1296.     move.l    (a5),d0
  1297.     move.l    d0,a5
  1298.     bne.b    .cw_sloop
  1299.  
  1300.     move.l    d7,a0
  1301.     call    UnlockIBase
  1302.  
  1303.     move.l    sp,a5
  1304. .cw_closew    move.l    (a5),d0
  1305.     beq.b    .cw_cwdone
  1306.     move.l    d0,a3
  1307.  
  1308.     move.l    (wd_WScreen,a3),a2
  1309.  
  1310.     tst.l    (wd_MenuStrip,a3)
  1311.     beq.b    .cw_nomenu
  1312.     move.l    a3,a0
  1313.     call    ClearMenuStrip
  1314. .cw_nomenu    move.l    a3,a0
  1315.     call    CloseWindow
  1316.  
  1317.     moveq    #-1,d1
  1318.     tst.l    (sc_FirstWindow,a2)
  1319.     bne.b    .cw_kille
  1320.     move.w    (sc_Flags,a2),d0
  1321.     and.w    #SCREENTYPE,d0
  1322.     cmp.w    #CUSTOMSCREEN,d0
  1323.     bne.b    .cw_kille
  1324.     move.l    a2,d1
  1325. .cw_kille    move.l    d1,(a5)+
  1326.     bra.b    .cw_closew
  1327. .cw_cwdone
  1328.  
  1329. .cw_closes    move.l    (sp)+,d0
  1330.     beq.b    .cw_csdone
  1331.     bmi.b    .cw_closes
  1332.     move.l    d0,a0
  1333.     call    CloseScreen
  1334.     bra.b    .cw_closes
  1335. .cw_csdone
  1336.     movem.l    (sp)+,d7/a2-a3/a5-a6
  1337. .rts    rts
  1338.  
  1339.  
  1340. _DoSomeDos    move.l    (DosBase,pc),a5
  1341.     move.l    (_ExecBase,pc),a6
  1342.     sub.l    a1,a1
  1343.     call    FindTask
  1344.     move.l    d0,a0
  1345.     move.l    (TC_Userdata,a0),a2    a2=CLI structure
  1346.     exg    a5,a6
  1347.  
  1348.     move.l    (cli_Module,a2),d1
  1349.     call    UnLoadSeg        SegList may be zero.
  1350.  
  1351.     move.l    (cli_StandardInput,a2),d2
  1352.     move.l    (cli_CurrentInput,a2),d1
  1353.     clr.l    (cli_StandardInput,a2)
  1354.     clr.l    (cli_CurrentInput,a2)
  1355.     cmp.l    d1,d2
  1356.     beq.b    .samei
  1357.     call    Close
  1358. .samei    move.l    d2,d1
  1359.     call    Close
  1360.     move.l    (cli_StandardOutput,a2),d2
  1361.     move.l    (cli_CurrentOutput,a2),d1
  1362.     clr.l    (cli_StandardOutput,a2)
  1363.     clr.l    (cli_CurrentOutput,a2)
  1364.     cmp.l    d1,d2
  1365.     beq.b    .sameo
  1366.     call    Close
  1367. .sameo    move.l    d2,d1
  1368.     call    Close
  1369.  
  1370.     cmp.w    #39,(LIB_VERSION,a6)
  1371.     bhs.b    .no_workaround
  1372.     exg    a5,a6
  1373.     lea    (cli_SetName,a2),a0
  1374.     bsr.b    .freeBSTR
  1375.     lea    (cli_CommandName,a2),a0
  1376.     bsr.b    .freeBSTR
  1377.     lea    (cli_Prompt,a2),a0
  1378.     bsr.b    .freeBSTR
  1379.     lea    (cli_CommandFile,a2),a0
  1380.     bsr.b    .freeBSTR
  1381.     exg    a5,a6
  1382. .no_workaround
  1383.     moveq    #DOS_CLI,d1
  1384.     move.l    a2,d2
  1385.     lsr.l    #2,d2
  1386.     jmp    (_LVOFreeDosObject,a6)
  1387.  
  1388. .freeBSTR    move.l    (a0),a1
  1389.     add.l    a1,a1
  1390.     clr.l    (a0)
  1391.     add.l    a1,a1
  1392.     jmp    (_LVOFreeVec,a6)
  1393.  
  1394.  
  1395. ;  IN: a3=ptr to buffer
  1396. ;      a6=execbase
  1397. SegTrackerInfo    movem.l    d0-a6,-(sp)
  1398.     clr.b    (a3)+
  1399.     lea    (SegTrackerName,pc),a1
  1400.     call    FindSemaphore
  1401.     tst.l    d0
  1402.     beq    .done2
  1403. .foundit    move.l    d0,a0
  1404.     move.l    (SS_SIZE,a0),d6        Get SegTracker 'find' routine
  1405.     lea    (.STTable,pc),a4
  1406.     lea    (-5*4,sp),sp
  1407.     moveq    #16,d5
  1408.     bra.b    .do_more
  1409. .do_more2    call    Permit
  1410. .do_more    move.l    a4,(sp)
  1411.     addq.l    #4,a4
  1412.     move.w    (a4)+,d0
  1413.     bmi.b    .done
  1414.     move.l    (a5,d0.w),a0
  1415.     move.l    a0,(4,sp)
  1416.     lea    (12,sp),a1
  1417.     lea    (16,sp),a2
  1418.     call    Forbid
  1419.     exg    d6,a6
  1420.     jsr    (a6)
  1421.     exg    d6,a6
  1422.     move.l    d0,(8,sp)
  1423.     beq.b    .do_more2
  1424.  
  1425.     subq.l    #1,a3
  1426.     lea    (.STFmt,pc),a0
  1427.     move.l    sp,a1
  1428.     lea    (PutChar,pc),a2
  1429.     call    RawDoFmt
  1430.  
  1431. .goforit    tst.b    (a3)+
  1432.     bne.b    .goforit
  1433.     call    Permit
  1434.     subq.l    #1,d5
  1435.     bne.b    .do_more
  1436.  
  1437. .done    lea    (5*4,sp),sp
  1438. .done2    movem.l    (sp)+,d0-a6
  1439.     rts
  1440.  
  1441.     ;     0  000000001111111111222222222233333333334444
  1442.     ;     1  234567890123456789012345678901234567890123
  1443.     ;    10,'xxxx=xxxxxxxx points to '', hunk xx:xxxxxx',0
  1444. .STFmt    dc.b    10,'%-.4s=%08lx points to ''%-.28s'', hunk %02lx:%06lx',0
  1445.     CNOP    0,2
  1446.  
  1447. STENTRY    MACRO
  1448.     dc.l    \1
  1449.     dc.w    \2
  1450.     ENDM
  1451.  
  1452. .STTable    STENTRY    <'  PC'>,CD_ProgramCounter
  1453.     STENTRY    <'  A0'>,CD_AddrReg_0
  1454.     STENTRY    <'  A1'>,CD_AddrRegs_1_6
  1455.     STENTRY    <'  A2'>,CD_AddrRegs_1_6+4
  1456.     STENTRY    <'  A3'>,CD_AddrRegs_1_6+8
  1457.     STENTRY    <'  A4'>,CD_AddrRegs_1_6+12
  1458.     STENTRY    <'  A5'>,CD_AddrRegs_1_6+16
  1459.     STENTRY    <'  A6'>,CD_AddrRegs_1_6+20
  1460.     STENTRY    <'  SP'>,CD_StackPtr
  1461.     STENTRY    <'S:00'>,CD_StackFrame+0
  1462.     STENTRY    <'S:02'>,CD_StackFrame+0+2
  1463.     STENTRY    <'S:04'>,CD_StackFrame+4
  1464.     STENTRY    <'S:06'>,CD_StackFrame+4+2
  1465.     STENTRY    <'S:08'>,CD_StackFrame+8
  1466.     STENTRY    <'S:0A'>,CD_StackFrame+8+2
  1467.     STENTRY    <'S:0C'>,CD_StackFrame+12
  1468.     STENTRY    <'S:0E'>,CD_StackFrame+12+2
  1469.     STENTRY    <'S:10'>,CD_StackFrame+16
  1470.     STENTRY    <'S:12'>,CD_StackFrame+16+2
  1471.     STENTRY    <'S:14'>,CD_StackFrame+20
  1472.     STENTRY    <'S:16'>,CD_StackFrame+20+2
  1473.     STENTRY    <'S:18'>,CD_StackFrame+24
  1474.     STENTRY    <'S:1A'>,CD_StackFrame+24+2
  1475.     STENTRY    <'S:1C'>,CD_StackFrame+28
  1476.     STENTRY    <'S:1E'>,CD_StackFrame+28+2
  1477.     STENTRY    <'S:20'>,CD_StackFrame+32
  1478.     STENTRY    <'S:22'>,CD_StackFrame+32+2
  1479.     STENTRY    <'S:24'>,CD_StackFrame+36
  1480.     STENTRY    <'S:26'>,CD_StackFrame+36+2
  1481.     STENTRY    <'S:28'>,CD_StackFrame+40
  1482.     STENTRY    <'S:2A'>,CD_StackFrame+40+2
  1483.     STENTRY    <'S:2C'>,CD_StackFrame+44
  1484.     STENTRY    <'S:2E'>,CD_StackFrame+44+2
  1485.     STENTRY    <'S:30'>,CD_StackFrame+48
  1486.     STENTRY    <'S:32'>,CD_StackFrame+48+2
  1487.     STENTRY    <'S:34'>,CD_StackFrame+52
  1488.     STENTRY    <'S:36'>,CD_StackFrame+52+2
  1489.     STENTRY    <'S:38'>,CD_StackFrame+56
  1490.     STENTRY    <'S:3A'>,CD_StackFrame+56+2
  1491.     STENTRY    <'S:3C'>,CD_StackFrame+60
  1492.     STENTRY    0,-1
  1493.  
  1494.  
  1495. ; This is the new patch method, it uses execbase TaskTrapCode for
  1496. ; NT_TASK and simple compare before adding task for NT_PROCESS.
  1497. ; Simple and clean, no need for Forbid()/Permit() for example.
  1498.  
  1499.     CNOP    0,4
  1500. AddTaskCode    cmp.b    #NT_PROCESS,(LN_TYPE,a1)
  1501.     bne.b    .addtask
  1502.     move.l    (TC_TRAPCODE,a1),d0
  1503.     beq.b    .change
  1504.     cmp.l    (DefProcTrap,pc),d0
  1505.     bne.b    .addtask
  1506. .change    move.l    (TrapEntryPtr,pc),(TC_TRAPCODE,a1)
  1507. .addtask    jmp    'addt'
  1508. _ATC_orig    EQU    *-4
  1509.  
  1510.  
  1511.  
  1512. ; Exception handler for 68000:
  1513. ; Stack when TC_TRAPCODE is entered for bus error/address error:
  1514. ;    LONG    Exception number
  1515. ;    WORD    Status, 0..2 function code, 3 inst/not inst, 4 read/write
  1516. ;    LONG    Access address
  1517. ;    WORD    Status register
  1518. ;    LONG    Program counter
  1519.  
  1520. ; Stack when TC_TRAPCODE is entered for other errors:
  1521. ;    LONG    Exception number
  1522. ;    WORD    Status register
  1523. ;    LONG    Program counter
  1524.  
  1525.     CNOP    0,4
  1526. NUM_SAVE_REGS    EQU    2
  1527. NewHandler000    movem.l    d0/a0,-(sp)
  1528.     move.l    usp,a0        store to user stack
  1529.     move.l    a0,d0
  1530.     and.w    #$fffe,d0    force stack even
  1531.     exg    d0,a0
  1532.     move.l    d0,-(a0)    save old user stack pointer
  1533.     move.l    sp,-(a0)    save supervisor stack pointer
  1534.     addq.l    #NUM_SAVE_REGS*4,(a0)        fix ssp
  1535.  
  1536.     move.l    (NUM_SAVE_REGS*4,sp),d0        exception number
  1537.     cmp.w    #2,d0
  1538.     beq.b    .isbuserror
  1539.     cmp.w    #3,d0
  1540.     bne.b    .not_addrerror
  1541. .isbuserror
  1542.     move.l    (8+NUM_SAVE_REGS*4+8,sp),-(a0)    pclower <<16 | xxxx
  1543.     move.l    (8+NUM_SAVE_REGS*4+4,sp),-(a0)    sr <<16 | pcupper
  1544.     move.l    d0,-(a0)            exception number
  1545.     move.l    a0,usp
  1546.     lea    (Trap_UserPart,pc),a0
  1547.     move.l    a0,(8+NUM_SAVE_REGS*4+4+2,sp)    change PC
  1548.     bra.b    _exithandler2
  1549. .not_addrerror
  1550.     move.l    (NUM_SAVE_REGS*4+8,sp),-(a0)    pclower <<16 | xxxx
  1551.     move.l    (NUM_SAVE_REGS*4+4,sp),-(a0)    sr <<16 | pcupper
  1552.     move.l    d0,-(a0)            exception number
  1553.     bra.b    _exithandler1
  1554.  
  1555.  
  1556. ; Exception handler for 68010 and better:
  1557. ; Stack when TC_TRAPCODE is entered:
  1558. ;    LONG    Exception number
  1559. ;    WORD    Status register
  1560. ;    LONG    Program counter
  1561. ;    WORD    Frametype & Vector-address (random data for 68000)
  1562. ;    ...    Additional processor state information
  1563.  
  1564.     CNOP    0,4
  1565. ;NUM_SAVE_REGS    EQU    2        MUST BE SAME AS WITH NewHandler000
  1566. NewHandler010    movem.l    d0/a0,-(sp)
  1567.     move.l    usp,a0        store to user stack
  1568.     move.l    a0,d0
  1569.     and.w    #$fffc,d0    force stack longword aligned
  1570.     exg    d0,a0
  1571.     move.l    d0,-(a0)    save old user stack pointer
  1572.     move.l    sp,-(a0)    save supervisor stack pointer
  1573.     addq.l    #NUM_SAVE_REGS*4,(a0)        fix ssp
  1574.     move.l    (NUM_SAVE_REGS*4+8,sp),-(a0)    pclower <<16 | ftype_vecaddr
  1575.     move.l    (NUM_SAVE_REGS*4+4,sp),-(a0)    sr <<16 | pcupper
  1576.     move.l    (NUM_SAVE_REGS*4,sp),-(a0)    exception number
  1577. _exithandler1    move.l    a0,usp
  1578.     lea    (Trap_UserPart,pc),a0
  1579.     move.l    a0,(NUM_SAVE_REGS*4+4+2,sp)    change PC
  1580. _exithandler2    movem.l    (sp)+,d0/a0
  1581.     addq.l    #4,sp                skip exception number
  1582.     rte                    go to userpart
  1583.  
  1584. ; Stack:    LONG    Exception number
  1585. ;    WORD    Status register
  1586. ;    LONG    Program counter
  1587. ;    WORD    Frametype & Vector-address
  1588. ;    LONG    Supervisor stack pointer
  1589. ;    LONG    Old User stack pointer
  1590. ;    [WORD    if usp wasn't longword aligned, 68010+]
  1591. ;    [BYTE   if usp wasn't even]
  1592. ;    ... old stack ...
  1593.  
  1594.     CNOP    0,4
  1595. Trap_UserPart    move.l    a0,-(sp)
  1596.     IFD    HACKSEMAPHORE
  1597.     lea    (CrashData,pc),a0
  1598. .wait    tst.l    (a0)
  1599.     bne.b    .wait
  1600.     addq.l    #1,(a0)
  1601.     ELSE
  1602.     move.l    a6,-(sp)             save a6
  1603.     move.l    (_ExecBase,pc),a6
  1604.     lea    (CrashData,pc),a0
  1605.     call    ObtainSemaphore            preserves d0-d1/a1
  1606.     move.l    (sp)+,a6
  1607.     ENDC
  1608.     movem.l    d0-d7,(CD_DataRegs,a0)        store all data regs
  1609.     movem.l    a1-a6,(CD_AddrRegs_1_6,a0)    store a1-a6
  1610.     move.l    (sp)+,(CD_AddrReg_0,a0)        store a0
  1611.     move.l    (sp)+,(CD_ExceptionNumber,a0)
  1612.     move.w    (sp),(CD_StatusRegister,a0)    store sr
  1613.     move.l    (2,sp),(CD_ProgramCounter,a0)    store pc
  1614.     addq.l    #8,sp
  1615.     move.l    (sp)+,(CD_SuperStackPtr,a0)
  1616.     move.l    (sp)+,(CD_UserStackPtr,a0)
  1617.  
  1618.     move.l    (_ExecBase,pc),a6
  1619.     sub.l    a1,a1
  1620.     move.l    a0,-(sp)
  1621.     call    FindTask
  1622.     move.l    (sp)+,a0
  1623.     move.l    d0,(CD_Task,a0)
  1624.     move.l    d0,a5
  1625.  
  1626.     ; Ask SmartCrash.manager to launch SubCode for us
  1627.     pea    MN_SIZE            MN_REPLYPORT:16, MN_LENGTH
  1628.     clr.l    -(sp)            LN_NAME:16, MN_REPLYPORT:16
  1629.     pea    MMTYPE_REPORT<<8    LN_TYPE, LN_PRI, LN_NAME:16
  1630.     clr.l    -(sp)            LN_PRED
  1631.     clr.l    -(sp)            LN_SUCC
  1632.     move.l    sp,a1
  1633.     move.l    (MsgPort,pc),a0
  1634.     call    PutMsg
  1635.  
  1636.     ; Go to deep sleep, from which we possibly wake up with WAKE_SIGNAL
  1637.     moveq    #0,d0
  1638.     call    Wait
  1639.     lea    (MN_SIZE,sp),sp
  1640.  
  1641.     ; Here TC_TRAPDATA is used to pass arguments (CD_CD).
  1642.     ; Passed stack CD CD_Task points to sigtask to send
  1643.     ; CD_sigf_SKIPPED signal when skip is done.
  1644.  
  1645.     IFD    FINDTASKBUG
  1646.     move.l    (CrashData+CD_Task,pc),a5
  1647.     ENDC
  1648.     move.l    (TC_TRAPDATA,a5),a0
  1649.     move.l    (CD_PrevTRAPDATA-CD_ExceptionNumber,a0),(TC_TRAPDATA,a5)
  1650.  
  1651.     move.w    (CD_Action-CD_ExceptionNumber,a0),d0
  1652.     ;add.w    d0,d0
  1653.     move.w    .tab(pc,d0.w),d0
  1654.     jmp    .tab(pc,d0.w)
  1655. .tab    dc.w    .action_skip-.tab    0 ACTION_SKIP
  1656.     dc.w    .action_exit-.tab    2 ACTION_EXIT
  1657.     dc.w    .action_jmp-.tab    4 ACTION_JMP
  1658.  
  1659. .action_skip    ; Skip faulty instruction:
  1660.  
  1661.     move.l    (CD_ProgramCounter-CD_ExceptionNumber,a0),a1
  1662.     move.l    (CD_ExceptionNumber-CD_ExceptionNumber,a0),d0
  1663.     moveq    #0,d1
  1664.     cmp.w    #4,d0            illegal instruction (advance PC with 2)
  1665.     seq    d1
  1666.     add.w    d1,d1
  1667.     cmp.w    #$A,d0            line-a emulator    (advance PC with 2)
  1668.     seq    d1
  1669.     add.w    d1,d1
  1670.     cmp.w    #$B,d0            line-f emulator (adcanve PC with 2/4/6)
  1671.     seq    d1
  1672.     bne.b    .not_fline        Test mmu-instructions
  1673.  
  1674.     move.w    (a1),d3            read instruction word
  1675.     move.w    d3,d2
  1676.     cmp.w    #%1111000001111100,d2    PTRAPcc (68851)
  1677.     beq.b    .add2
  1678.     cmp.w    #%1111000001111010,d2    PTRAPcc.W #<data> (68851)
  1679.     beq.b    .add4
  1680.     cmp.w    #%1111000001111011,d2    PTRAPcc.L #<data> (68851)
  1681.     beq.b    .add6
  1682.     and.w    #%1111111111000000,d2
  1683.     cmp.w    #%1111000010000000,d2    PBcc.w <disp> (68851)
  1684.     beq.b    .add2
  1685.     cmp.w    #%1111000011000000,d2    PBcc.L <disp> (68851)
  1686.     beq.b    .add4
  1687.     cmp.w    #%1111000000000000,d2    PMOVE/PLOAD/PVALID/PFLUSH*/PTEST
  1688.     beq.b    .add2
  1689.     cmp.w    #%1111100000000000,d2    TBLU*/TBLS*/LPSTOP? (CPU32)
  1690.     bne.b    .not_cpu32
  1691.     cmp.w    #%0000000111000000,(2,a1) LPSTOP #<data> (CPU32, 68060)
  1692.     beq.b    .add4
  1693.     bra.b    .add2
  1694. .not_cpu32
  1695.     move.w    d3,d2
  1696.     and.w    #%1111111111111000,d2
  1697.     cmp.w    #%1111000001001000,d2    PDBcc Dn,<disp> (68851)
  1698.     beq.b    .add4
  1699.     cmp.w    #%1111011000100000,d2    MOVE16 (an)+,(an)+ (68040+)
  1700.     beq.b    .add2
  1701.     and.w    #%1111111111000000,d2
  1702.     cmp.w    #%1111000001000000,d2    PScc (68851)
  1703.     beq.b    .add2
  1704.     move.w    d3,d2
  1705.     and.w    #%1111111111100000,d2
  1706.     cmp.w    #%1111011000000000,d2    MOVE16 absolute long address src or dst (68040+)
  1707.     beq.b    .add4
  1708.     bra.b    .not_fline
  1709.  
  1710. .add6    addq.l    #2,a1            advance PC with total 8
  1711. .add4    addq.l    #2,a1            advance PC with total 6
  1712. .add2    addq.l    #2,a1            advance PC with total 4
  1713.  
  1714. .not_fline    tst.w    d1            illegal inst/a-line/f-line ?
  1715.     beq.b    .no_add
  1716.     addq.l    #2,a1            advance PC with 2
  1717. .no_add    cmp.w    #8,d0            privilege violation
  1718.     bne.b    .no_privilege
  1719.     cmp.l    #%11111000000000000000000111000000,(a1) LPSTOP #<data> (CPU32, 68060)
  1720.     beq.b    .lpstop
  1721.     move.w    (a1)+,d3        read instruction word, advance PC with 2
  1722.     lea    (.privtable,pc),a2
  1723. .poloop    move.w    (a2)+,d2
  1724.     beq.b    .pdone
  1725. .piloop    move.w    (a2)+,d1
  1726.     beq.b    .poloop
  1727.     and.w    d3,d1
  1728.     cmp.w    (a2)+,d1
  1729.     bne.b    .piloop
  1730.     add.w    d2,a1            advance PC (BUG: was add.l)
  1731.     ;;bra.b    .piloop
  1732. .pdone
  1733.     bra.b    .no_privilege
  1734.  
  1735. .lpstop    addq.l    #4,a1            advance PC with total 6 bytes
  1736. .no_privilege
  1737.  
  1738.  
  1739. ;  IN: a1=PC to jump to
  1740. .gotopc    lea    (.SuperCode,pc),a5
  1741.     call    Supervisor
  1742. .SuperCode    ;move.w    #$2700,sr
  1743.  
  1744.     ; write SR
  1745.     move.w    (CD_StatusRegister-CD_ExceptionNumber,a0),(sp)
  1746.     ; write PC
  1747.     move.l    a1,(2,sp)
  1748.     ; write USP
  1749.     move.l    (CD_UserStackPtr-CD_ExceptionNumber,a0),a1
  1750.     move.l    a1,usp
  1751.     ; write D0-D7
  1752.     movem.l    (CD_DataRegs-CD_ExceptionNumber,a0),d0-d7
  1753.     ; write A1-A6
  1754.     movem.l    (CD_AddrRegs_1_6-CD_ExceptionNumber,a0),a1-a6
  1755.     move.l    (CD_AddrReg_0-CD_ExceptionNumber,a0),-(sp)
  1756.     movem.l    d0-d1/a1/a6,-(sp)
  1757.     move.l    (_ExecBase,pc),a6
  1758.     ; Get sigtask
  1759.     move.l    (CD_Task-CD_ExceptionNumber,a0),a1
  1760.     IFD    FIXED_SKIPPED_SIGNAL
  1761.     move.l    #1<<FIXED_SKIPPED_SIGNAL,d0
  1762.     ELSE
  1763.     ; Get sigmask
  1764.     move.l    (CD_sigf_SKIPPED-CD_ExceptionNumber,a0),d0
  1765.     ENDC
  1766.     ; Must not use CD pointed by a0 after Signal call!
  1767.     call    Signal
  1768.     movem.l    (sp)+,d0-d1/a1/a6
  1769.     ; write A0
  1770.     move.l    (sp)+,a0
  1771.     rte
  1772.  
  1773.  
  1774. .action_jmp    ; jump to address (address in CD_ProgramCounter)
  1775.     move.l    (CD_ProgramCounter-CD_ExceptionNumber,a0),a1
  1776.     bra    .gotopc
  1777.  
  1778.  
  1779. .action_exit    ; Exit program with RC 0 (only NT_PROCESS will get here):
  1780.     move.l    (pr_ReturnAddr,a5),d0
  1781.     subq.l    #4,d0
  1782.     move.l    d0,sp
  1783.     moveq    #RETURN_OK,d0        ;-O
  1784.     rts
  1785.  
  1786. ;         1111111111111111  0000000000000000
  1787. ;         fedcba9876543210  fedcba9876543210    instruction
  1788. .privtable    dc.w    2    ; 2 word instructions
  1789.     dc.w    %1111111111111111,%0000001001111100    ANDI #<data>,sr
  1790.     dc.w    %1111111111111111,%0000101001111100    EORI #<data>,sr
  1791.     dc.w    %1111111111111111,%0000000001111100    ORI  #<data>,sr
  1792.     dc.w    %1111111111111110,%0100111001111010    MOVEC xx,xx
  1793.     dc.w    %1111111111111111,%0100111001110010    STOP #xx
  1794.     dc.w    %1111111111000000,%1111000000000000    mmu-instr (PMOVE/PLOAD/PVALID/PFLUSH*/PTEST)
  1795.     dc.w    %1111111111000000,%1111000010000000    PBcc.w <disp> (68851)
  1796.     dc.w    %1111111100000000,%0000111000000000    MOVES xx,xx
  1797.     dc.w    0
  1798.  
  1799.     dc.w    4    ; 3 word instructions
  1800.     dc.w    %1111111111111111,%1111000001111010    PTRAPcc.W #<data> (68851)
  1801.     dc.w    %1111111111111000,%1111000001001000    PDBcc Dn,<disp> (68851)
  1802.     dc.w    %1111111111000000,%1111000011000000    PBcc.L <disp> (68851)
  1803.     dc.w    %1111111111000000,%1111000001000000    PScc (68851)
  1804.     ; LPSTOP (CPU32,68060)  handled with special test
  1805.     dc.w    0
  1806.  
  1807.     dc.w    6    ; 4 word instructions
  1808.     dc.w    %1111111111111111,%1111000001111011    PTRAPcc.L #<data> (68851)
  1809.     dc.w    0
  1810.  
  1811.     dc.w    0    ; end mark
  1812.  
  1813.  
  1814.  
  1815.     IFD    INSTSIZE
  1816.  
  1817. ;  IN: d0.l=ULONG opcode1 <<16 | opcode2
  1818. ; OUT: d0.l=ULONG instruction size in bytes
  1819. InstSize    movem.l    d1-a6,-(sp)
  1820.     move.l    d0,d6
  1821.  
  1822.     ;int-inst        word1    encoding
  1823.     ;add/sub/and/or        8,7,6    000=byte 001=word 010=long
  1824.     ;adda/suba        8,7,6    011=word 111=long
  1825.     ;btst            8    1=bit number dynamic=byte
  1826.     ;chk            8,7    11=word 10=long
  1827.     ;cmp(a)            8,7,6    000=byte 001=word 010=long 011=word 111=long
  1828.     ;div*.w/mul*.w        -    word
  1829.     ;div*.l/mul*.l        -    long
  1830.     ;move SRC!        13,12    01=byte 11=word 10=long
  1831.     ;movea            13,12    11=word 10=long
  1832.     ;move to ccr        -    word
  1833.     ;tst            7,6    00=byte 01=word 10=long
  1834.  
  1835.     ;move to sr        -    word
  1836.     ;pflushr        -    word
  1837.     ;pmove #x,reg    w2: 13,12,11,10    0000=long 0001=quad 0010=quad 0011=quad
  1838.     ;                0100=byte 0101=byte 0110=byte 0111=word
  1839.     ;pmove.w #x,psr        -    word
  1840.  
  1841.     ;fpu-inst    word1    word2        encoding
  1842.     ;            14,13,12,11,10    10000=long 10001=single-precision
  1843.     ;                    10010=extended-precision
  1844.     ;                    10011=packed decimal real 10100=word
  1845.     ;                    10101=double-precision 10110=byte
  1846.     ; fmove.l #<xxx>,fpcr            long
  1847.     ; fmovem.l #<xxx>,<fpcrs>        long
  1848.     ;
  1849.     ; exluding:
  1850.     ; FBcc
  1851.     ; FDBcc
  1852.     ; fmove.l fpcr,<ea>
  1853.     ; fmovem.l <fpcsr>,<ea>
  1854.     ; fmove.<fmt> fpm,<ea>
  1855.     ; fmovem.x (fpdr)
  1856.     ; fnop
  1857.     ; FScc
  1858.     ; FTRAPcc
  1859.  
  1860.     move.l    d6,d0
  1861.     move.w    d0,d1            d1=opcode2
  1862.     swap    d0            d0=opcode1
  1863.     and.w    #%0111111,d0        bit 7 clear = read <ea>
  1864.     bsr.b    handle_ea
  1865.  
  1866.     movem.l    (sp)+,d1-a6
  1867.     rts
  1868.  
  1869.  
  1870. ;  IN: d0.w=UWORD ea_bits (bit 7 set if dest <ea>, bits 0-6 encode <ea>)
  1871. ;      d1.w=UWORD opcode2
  1872. ;      d2.w=UWORD operation_size (only needed for instruction supporting immed data src)
  1873. ;    2=byte/word
  1874. ;    4=long/single-precision
  1875. ;    8=double-precision
  1876. ;    12=extended-precision/packed-decimal real
  1877. ; OUT: d0.l=ULONG ea size
  1878. handle_ea    movem.l    d1-d7,-(sp)
  1879.     move.l    d0,d5            d0=ea_bits <<16 | opcode2
  1880.     move.w    d0,d6            d6=opcode2
  1881.     swap    d5            d5=ea_bits
  1882.  
  1883.     move.w    d5,d0            ??????????xxxyyy
  1884.     lsr.w    #2,d0            00??????????xxxy
  1885.     and.w    #%01110,d0        000000000000xxx0
  1886.     move.w    .ea_jmp(pc,d0.w),d0
  1887.     jmp    .ea_jmp(pc,d0.w)
  1888.  
  1889. .ea_jmp    dc.w    .ea000-.ea_jmp
  1890.     dc.w    .ea001-.ea_jmp
  1891.     dc.w    .ea010-.ea_jmp
  1892.     dc.w    .ea011-.ea_jmp
  1893.     dc.w    .ea100-.ea_jmp
  1894.     dc.w    .ea101-.ea_jmp
  1895.     dc.w    .ea110-.ea_jmp
  1896.     dc.w    .ea111-.ea_jmp
  1897.  
  1898. .ea000    ; Dn                0
  1899.     moveq    #0,d0
  1900.     bra    .eadone
  1901. .ea001    ; An                0
  1902.     moveq    #0,d0
  1903.     bra    .eadone
  1904. .ea010    ; (An)                0
  1905.     moveq    #0,d0
  1906.     bra    .eadone
  1907. .ea011    ; (An)+                0
  1908.     moveq    #0,d0
  1909.     bra    .eadone
  1910. .ea100    ; -(An)                0
  1911.     moveq    #0,d0
  1912.     bra    .eadone
  1913. .ea101    ; (d16,An)            1
  1914. .ea111_000    ; (xxx).w            1
  1915. .ea111_010    ; (d16,PC)            1
  1916. .ea111_110    ; illegal
  1917.     moveq    #2,d0
  1918.     bra    .eadone
  1919. .ea111_001    ; (xxx).l            2
  1920. .ea111_101    ; illegal
  1921.     moveq    #4,d0
  1922.     bra    .eadone
  1923.  
  1924. .ea110    ; (d8,An,Xn.SIZE*SCALE)        1
  1925.     ; (bd,An,Xn.SIZE*SCALE)        1,2 or 3
  1926.     ; ([bd,An],Xn.SIZE*SCALE,od)    1,2,3,4 or 5
  1927.     ; ([bd,An,Xn.SIZE*SCALE],od)    1,2,3,4 or 5
  1928. .ea111_111    ; illegal
  1929. .ea111_011    ; (d8,PC,Xn.SIZE*SCALE)        1
  1930.     ; (bd,PC,Xn.SIZE*SCALE)        1,2 or 3
  1931.     ; ([bd,PC],Xn.SIZE*SCALE,od)    1,2,3,4 or 5
  1932.     ; ([bd,PC,Xn.SIZE*SCALE],od)    1,2,3,4 or 5
  1933.  
  1934.     ; Now we have an extension word, so lets examine the
  1935.     ; extension word type (bit 8 0=brief 1=full)
  1936.     moveq    #2,d0
  1937.     btst    #8,d6
  1938.     beq.b    .eadone            brief extension word, always 1 word
  1939.  
  1940.     ; full extension word, 1 to 5 words follow, lets
  1941.     ; examine how many exactly:
  1942.  
  1943. ; single effective address operation word format
  1944. ; 15 14 13 12 11 10  9  8  7  6  5  4  3  2  1  0
  1945. ;  x  x  x  x  x  x  x  x  x  x ==mode==  register
  1946.  
  1947. ; brief extension word format
  1948. ; 15 14 13 12 11 10  9  8  7  6  5  4  3  2  1  0
  1949. ; d/a registe w/l scale 0 =====displacement======
  1950.  
  1951. ; full extension word format
  1952. ; 15 14 13 12 11 10  9  8  7  6  5  4  3  2  1  0
  1953. ; d/a registe w/l scale 1  bs is bdsiz 0  ==i/is=
  1954. ; ======base displacement (0, 1, or 2 words)=====
  1955. ; =====outer displacement (0, 1, or 2 words)=====
  1956.  
  1957. ; d/a    index register type
  1958. ;    0 = dn
  1959. ;    1 = an
  1960. ; w/l    word/long-word index size
  1961. ;    0 = sign-extended word
  1962. ;    1 = long word
  1963. ; scale    scale factor
  1964. ;    00 = 1
  1965. ;    01 = 2
  1966. ;    10 = 4
  1967. ;    11 = 8
  1968. ; bs    base register suppress
  1969. ;    0 = base register added
  1970. ;    1 = base register suppressed
  1971. ; is    index suppress
  1972. ;    0 = evaluate and add index operand
  1973. ;    1 = suppress index operand
  1974. ; bd siz    base displacement size
  1975. ;    00 = reserved
  1976. ;    01 = null displacement
  1977. ;    10 = word displacement
  1978. ;    11 = long displacement
  1979. ; i/is    index/indirect selection
  1980. ;    indirect and indexing operand determined in
  1981. ;    conjunction with is
  1982. ;
  1983. ; is    i/is    operation
  1984. ; 0    000    no memory indirect action
  1985. ; 0    001    indirect preindexed with null outer displacement
  1986. ; 0    010    indirect preindexed with word outer displacement
  1987. ; 0    011    indirect preindexed with long outer displacement
  1988. ; 0    100    reserved
  1989. ; 0    101    indirect postindexed with null outer displacement
  1990. ; 0    110    indirect postindexed with word outer displacement
  1991. ; 0    111    indirect postindexed with long outer displacement
  1992. ; 1    000    no memory indirect action
  1993. ; 1    001    memory indirect with null outer displacement
  1994. ; 1    010    memory indirect with word outer displacement
  1995. ; 1    011    memory indirect with long outer displacement
  1996. ; 1    100    reserved
  1997. ; 1    101    reserved
  1998. ; 1    110    reserved
  1999. ; 1    111    reserved
  2000.  
  2001.     ; `bdsiz' is reserved (%00) ?
  2002.     moveq    #0,d0
  2003.     move.w    d6,d1
  2004.     and.w    #%00110000,d1
  2005.     beq    .eadone            illegal
  2006.     ; mask in `is' and `i/is'
  2007.     move.w    d6,d1
  2008.     and.w    #%01000111,d1
  2009.     cmp.w    #%00000100,d1        `is'=0 `i/is'=100 is reserved, and
  2010.     beq.b    .eadone            thus illegal
  2011.     btst    #6,d1            `is' clear?
  2012.     beq.b    .not_res        clear, rest of the bit patterns ok
  2013.     btst    #2,d1            set, rest of the patterns with
  2014.     bne.b    .eadone            bit 2 set are illegal
  2015. .not_res
  2016.     moveq    #2,d0            default 1 word
  2017.     ; get base displacement size
  2018.     move.w    d6,d1            ??????????xx????
  2019.     lsr.w    #4,d1            0000??????????xx
  2020.     and.w    #%011,d1        00000000000000xx
  2021.     beq.b    .bd_n
  2022.     subq.w    #1,d1            0,1 or 2
  2023.     add.w    d1,d0
  2024.     add.w    d1,d0            add 0 2 or 4
  2025. .bd_n
  2026.     ; get outer displacement size
  2027.     move.w    d6,d1
  2028.     and.w    #%011,d1
  2029.     beq.b    .od_n
  2030.     subq.w    #1,d1            0,1 or 2
  2031.     add.w    d1,d0
  2032.     add.w    d1,d0            add 0 2 or 4
  2033. .od_n
  2034.     ; result: d0.l = 2, 4, 6, 8 or 10
  2035.     bra    .eadone
  2036.  
  2037.  
  2038. .ea111_100    ; #<xxx>            1,2,4 or 6
  2039.     moveq    #2,d0
  2040.     add.w    d2,d0
  2041.     bra    .eadone
  2042.  
  2043. .ea111    move.w    d5,d0            ??????????xxxyyy
  2044.     lsl.w    #1,d0            ?????????xxxyyy0
  2045.     and.w    #%01110,d0        000000000000yyy0
  2046.     move.w    .ea111_jmp(pc,d0.w),d0
  2047.     jmp    .ea111_jmp(pc,d0.w)
  2048.  
  2049. .ea111_jmp    dc.w    .ea111_000-.ea111_jmp
  2050.     dc.w    .ea111_001-.ea111_jmp
  2051.     dc.w    .ea111_010-.ea111_jmp
  2052.     dc.w    .ea111_011-.ea111_jmp
  2053.     dc.w    .ea111_100-.ea111_jmp
  2054.     dc.w    .ea111_101-.ea111_jmp    illegal
  2055.     dc.w    .ea111_110-.ea111_jmp    illegal
  2056.     dc.w    .ea111_111-.ea111_jmp    illegal
  2057.  
  2058.  
  2059. .eadone    ; d0.w=number of bytes in extension word(s)
  2060.  
  2061.     movem.l    (sp)+,d1-d7
  2062.     rts
  2063.  
  2064.  
  2065.     ENDC
  2066.  
  2067.  
  2068.     ;
  2069.     ; If you wonder how to generate this following
  2070.     ; file:
  2071.     ;
  2072.     ; Compile RequestLong.ASM and execute it.
  2073.     ; Included binary saver (bin.saver.ASM) will
  2074.     ; generate requestlong.bin file.
  2075.  
  2076. RequestLong    incbin    "source:requestlong.bin"
  2077.  
  2078.  
  2079. AllocPatch
  2080. _idpos    dc.l    SMARTCRASH13_ID            4
  2081. _jmppos    jmp    'addt'                6
  2082. JMPADDROFFS    EQU    *-4-AllocPatch
  2083. TrapEntry    move.l    a0,-(sp)            2
  2084.     move.l    #'exec',a0            6
  2085. _ExecBase    EQU    *-4
  2086.     move.l    (ThisTask,a0),a0        4
  2087.     cmp.b    #NT_PROCESS,(LN_TYPE,a0)    6
  2088.     move.l    (sp)+,a0            2
  2089.     bne.b    TTaskCode            2
  2090.     jmp    'proc'                6
  2091. TrapProc    EQU    *-4
  2092. TTaskCode    jmp    'task'                6 =44
  2093. TrapTask    EQU    *-4
  2094. AllocPatch_SIZEOF    EQU    (*-AllocPatch+3)&-4
  2095.  
  2096. SetManPortName    dc.b    'SetMan',0
  2097. IntuiName    dc.b    'intuition.library',0
  2098. TaskName    dc.b    'SmartCrash.manager',0
  2099. SubName    dc.b    'SmartCrash.req',0
  2100. PortName    dc.b    'SmartCrash.port',0
  2101. WindowTitle    dc.b    'SmartCrash 1.3.0 Copyright © 1995-2000 Harry "Piru" Sintonen',0
  2102. SegTrackerName    dc.b    'SegTracker',0
  2103.  
  2104. BodyFmt    dc.b    'Exception %lx%s%s%s',10
  2105.     dc.b    'Task: %08lx  PC: %08lx  SR: %04lx  USP: %08lx  SSP: %08lx',10
  2106.     dc.b    'D: %08lx %08lx %08lx %08lx %08lx %08lx %08lx %08lx',10
  2107.     dc.b    'A: %08lx %08lx %08lx %08lx %08lx %08lx %08lx %08lx',10
  2108.     dc.b    'S: %08lx %08lx %08lx %08lx %08lx %08lx %08lx %08lx',10
  2109.     dc.b    'S: %08lx %08lx %08lx %08lx %08lx %08lx %08lx %08lx',10
  2110.     dc.b    '%.7s: %-.60s',10
  2111.     dc.b    '%s',0
  2112.  
  2113. sTask    dc.b    'Task',0
  2114. sProcess    dc.b    'Process'        No need to zero terminate
  2115. sCommand    dc.b    'Command'
  2116.  
  2117. sKnown    dc.b    ': ',0
  2118. NullStr    EQU    *-1
  2119.  
  2120.     CNOP    0,2
  2121. ExceptionTable
  2122. .s    dc.w    -1,-1,s2-.s,s3-.s,s4-.s,s5-.s,s6-.s,s7-.s
  2123.     dc.w    s8-.s,s9-.s,s10-.s,s11-.s,-1,s13-.s,s14-.s,s15-.s
  2124.     dc.w    -1,-1,-1,-1,-1,-1,-1,-1
  2125.     dc.w    s24-.s,-1,-1,-1,-1,-1,-1,-1
  2126.     dc.w    s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s
  2127.     dc.w    s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s,s2x-.s
  2128.     dc.w    s48-.s,s49-.s,s50-.s,s51-.s,s52-.s,s53-.s,s54-.s,s55-.s
  2129.     dc.w    s56-.s,s57-.s,s58-.s,-1
  2130.     dc.w    s60-.s,s61-.s
  2131.     dc.w    -1,-1
  2132.  
  2133. s2    dc.b    'bus error',0
  2134. s3    dc.b    'address error',0
  2135. s4    dc.b    'illegal instruction',0
  2136. s5    dc.b    'zero divide',0
  2137. s6    dc.b    'chk instruction',0
  2138. s7    dc.b    'trapcc instruction',0
  2139. s8    dc.b    'privilege violation',0
  2140. s9    dc.b    'trace',0
  2141. s10    dc.b    'line-a emulator',0
  2142. s11    dc.b    'line-f emulator',0
  2143. s13    dc.b    'coprocessor protocol violation',0    ;020/030
  2144. s14    dc.b    'format error',0
  2145. s15    dc.b    'uninitialized interrupt',0
  2146. s24    dc.b    'spurious interrupt',0
  2147. s2x    dc.b    'trap instruction #',0
  2148. s48    dc.b    'FP bsun',0                ;88x/040/060
  2149. s49    dc.b    'FP inexact result',0            ;88x/040/060
  2150. s50    dc.b    'FP zero divide',0            ;88x/040/060
  2151. s51    dc.b    'FP underflow',0            ;88x/040/060
  2152. s52    dc.b    'FP operand error',0            ;88x/040/060
  2153. s53    dc.b    'FP overflow',0                ;88x/040/060
  2154. s54    dc.b    'FP signaling NAN',0            ;88x/040/060
  2155. s55    dc.b    'FP unimplemented data type',0        ;040/060
  2156. s56    dc.b    'MMU configuration',0            ;030/851
  2157. s57    dc.b    'MMU illegal operation',0        ;851
  2158. s58    dc.b    'MMU access level violation',0        ;851
  2159. s60    dc.b    'unimplemented effective address',0    ;060
  2160. s61    dc.b    'unimplemented integer instruction',0    ;060
  2161.  
  2162. GadgetFmt    dc.b    'S%skip|%sRemove|E%sxit|%sDebug|Reboot|%sJMP...|R%sTS|%sSuspend',0
  2163. UnderlStr    dc.b    '_',0
  2164. CLIFmt    dc.b    'CLI[%ld]: %-.54b',0
  2165.  
  2166. AT_LOCATE_P    MACRO    ; x,y
  2167. _AT_X    SET    \1
  2168. _AT_Y    SET    \2
  2169.     ENDM
  2170.  
  2171. AT_LOCATE    MACRO    ; xchar,ychar
  2172. _AT_X    SET    _AT_INITX+(\1*8)
  2173.     IFGT    NARG-1
  2174. _AT_Y    SET    _AT_INITY+(\2*_AT_YSPACE)
  2175.     ENDC
  2176.     ENDM
  2177.  
  2178. AT_SETYSPACE    MACRO    ; yspacing
  2179. _AT_YSPACE    SET    \1
  2180.     ENDM
  2181.  
  2182. AT_INIT    MACRO    ; [inityadd]
  2183. _AT_INITX    SET    16
  2184. _AT_WIDTH    SET    (640-_AT_INITX*2)/2
  2185.     IFGT    NARG
  2186. _AT_INITY    SET    12+\1
  2187.     ELSE
  2188. _AT_INITY    SET    12
  2189.     ENDC
  2190. _AT_X    SET    _AT_INITX
  2191. _AT_Y    SET    _AT_INITY
  2192.     AT_SETYSPACE    8
  2193. _AT_YMAX    SET    _AT_Y+_AT_YSPACE
  2194. _AT_FST    SET    0
  2195.     ENDM
  2196.  
  2197. AT_PRINT    MACRO
  2198.     IFEQ    _AT_FST
  2199. _AT_FST    SET    1
  2200.     ELSE
  2201.     dc.b    0,-1
  2202.     ENDC
  2203.     dc.b    (_AT_X/256)
  2204.     dc.b    (_AT_X&255)
  2205.     dc.b    _AT_Y
  2206.  
  2207. _AT_Y    SET    _AT_Y+_AT_YSPACE
  2208.     IFGT    _AT_Y-_AT_YMAX
  2209. _AT_YMAX    SET    _AT_Y
  2210.     ENDC
  2211. _AT_X    SET    _AT_INITX
  2212.     ENDM
  2213.  
  2214. AT_END    MACRO    ; helabel
  2215.     dc.b    0,0
  2216. \1    dc.b    _AT_YMAX
  2217.     ENDM
  2218.  
  2219. AT_CENTRE    MACRO    ;nextstringslen
  2220.     AT_LOCATE_P    _AT_INITX+_AT_WIDTH-\1*4,_AT_Y
  2221.     AT_PRINT
  2222.     ENDM
  2223.  
  2224.  
  2225. Alert01    AT_INIT        6
  2226.     AT_SETYSPACE    13
  2227.     AT_CENTRE    22
  2228.     dc.b        "Software Failure Alert"
  2229.     AT_SETYSPACE    16
  2230.     AT_CENTRE    34
  2231.     dc.b        "(couln't create failure requester)"
  2232.     AT_SETYSPACE    18
  2233.     AT_CENTRE    62
  2234. Alert01Buf    ds.b        62        'Error 00000000 at PC=00000000 Task=00000000 "NameOfTask"      '
  2235.     AT_CENTRE    46
  2236.     dc.b        "Press any mouse button to suspend the program."
  2237.     AT_END        Alert01_len
  2238. Alert01Fmt    dc.b        'Error %08lx at PC=%08lx Task=%08lx "%.17s',0
  2239.  
  2240.  
  2241.     CNOP    0,4
  2242. DT
  2243. DosBase    ds.l    1
  2244. IntuiBase    ds.l    1
  2245. _GfxBase    ds.l    1
  2246. RTBase    ds.l    1
  2247. MsgPort    ds.l    1
  2248. RecMem    ds.l    1
  2249. TrapEntryPtr    ds.l    1
  2250. SubTaskCnt    ds.l    1
  2251. sigb_EXITSUB    ds.l    1
  2252. sigf_EXITSUB    ds.l    1
  2253. sigf_REMOVED    ds.l    1
  2254. sigf_INITOK    ds.l    1
  2255. SigTask    ds.l    1
  2256. DefProcTrap    ds.l    1
  2257. DefTaskTrap    ds.l    1
  2258. FontBase    ds.l    1
  2259. _ThisTask    ds.l    1
  2260. HavePatchCtrl    ds.l    1
  2261.  
  2262. CrashData    ds.b    CD_SIZE
  2263.  
  2264.     CNOP    0,2
  2265. TAttr    ds.b    ta_SIZEOF
  2266. FontName    ds.b    MAXFONTNAMELEN
  2267.  
  2268.  
  2269. COPY_LEN    EQU    (*-COPY_START+3)&-4
  2270.  
  2271.     CNOP    0,4
  2272. sigb_REMOVED    ds.l    1
  2273. sigb_INITOK    ds.l    1
  2274. RDArgs    ds.l    1
  2275. ArgArray    ds.l    ARG_NUMARGS
  2276. SigThisTask    ds.l    1
  2277. Copy    ds.l    1
  2278.